* and ** Operators in Python Function Parameters

  • 2021-10-24 23:24:27
  • OfStack

Problem description

When reading some codes, we often see that the parameters of function definition/call are preceded by * or * * operator, which is confusing. Today, we will explore the record once.

* and ** when function is defined

Looking up the relevant data, we know that adding * before the parameters means that there are more than one parameter, while the parameters passed in by functions with one asterisk (*) are stored as one tuple (tuple), and those with two (*) are dictionaries (dict)!

We define three functions to test the functions of * and * under 1 respectively.

The first function func1 has two arguments in the argument list, where the argument b is preceded by *
The second function func2 has two arguments in the argument list, where the argument b is preceded by **
The third function func3 has three arguments in the argument list, the second argument is preceded by *, and the third argument is preceded by **


def func1(a, *b):
  print(a)
  print(b)
  
def func2(a, **b):
  print(a)
  print(b)
  
def func3(a, *b, **c):
  print(a)
  print(b)
  print(c)

Then we pass in parameters


func1(1, 2, 3, 4)
print("---"*24)
func2(1, x=1, y=2)
print("---"*24)
func3(1, 2, 3, 4, x=5, y=6)

The printed result is:

$python3 main.py

(2, 3, 4)
------------------------------------------------------------------------
1
{'x': 1, 'y': 2}
------------------------------------------------------------------------
1
(2, 3, 4)
{'x': 5, 'y': 6}

It can be seen that the first function assigns all the redundant subsequent parameters to the parameter b with * in tuple form, and the second function assigns redundant parameters to the parameter b with * * in dictionary form. When * and * * exist at the same time, the parameters passed by the function with one asterisk (*) parameter are stored as one tuple (tuple), and the dictionary with two (*) signs is represented by dict.

If we call func2 without passing in parameters in the form of assignment, the program will report an error, for example


func2(1, 2, 3, 4)
print("---"*24)

There will be the following error message:

Traceback (most recent call last):
File "main.py", line 18, in < module >
func2(1, 2, 3, 4)
TypeError: func2() takes 1 positional argument but 4 were given

The role of * and * * when invoked

When called, * is mainly used to extract the parameter list, which is applicable to data of type set, tuple, list and dict (whose value of values will be taken). The experimental code is as follows:


def func4(a, b):
  print(a)
  print(b)

params_set = (1, 2)
params_tuple = (1, 2)
params_list = [1, 2]
params_dict = {
  "a": 1,
  "b": 2
}

We use the * parameter to call them separately


print("***"*24)
func4(*params_set)
print("***"*24)
func4(*params_tuple)
print("***"*24)
func4(*params_list)
print("***"*24)
func4(*params_dict)
print("***"*24)

The printed result is as follows:

************************************************************************
1
2
************************************************************************
1
2
************************************************************************
1
2
************************************************************************
a
b
************************************************************************

It can be seen that * assigns parameters in order 11 (set is out of order, so the blind guess result is random and not verified by experiments), while dict type assigns keys of dictionary as function parameter.

** Parameter mode requires that the input must be 1 dict, and the variable name should be the same as the variable name defined by the function. The experimental code is as follows:


params_dict1 = {
  "a": 1,
  "b": 2
}
params_dict2 = {
  "x": 1,
  "y": 2
}

print("---"*24)
func4(**params_dict1)
print("---"*24)
func4(**params_dict2)

The printed result is as follows:

------------------------------------------------------------------------
1
2
------------------------------------------------------------------------
Traceback (most recent call last):
File "main.py", line 57, in < module >
func4(**params_dict2)
TypeError: func4() got an unexpected keyword argument 'x'

As you can see, when the variable name is different from the variable name defined by the function, the program will report an error

Reference

What does it mean in the Python function that arguments are preceded by * and * *?
Execute Python-3 Online (Python v3.6.2),


Related articles: