To call a function, you need to know the name and parameters of the function, such as the absolute value function abs, which receives one parameter.
You can view the documentation directly from Python’s official website:
http://docs.python.org/2/library/functions.html#abs
You can also view the abs function on the interactive command line through help(abs) help information.
Call the abs function:
>>> abs(100)
100
>>> abs(-20)
20
>>> abs(12.34)
12.34
When calling a function, if the number of parameters passed in is incorrect, a TypeError will be reported, and Python will clearly tell you: abs() has only one parameter, but two are given:
>> ;> abs(1, 2)
Traceback (most recent call last):
File "
TypeError: abs() takes exactly one argument (2 given)
If the number of parameters passed in is correct, but the parameter type cannot be accepted by the function, a TypeError error will be reported and the error message will be given: str is the wrong parameter type:
>>> abs ('a')
Traceback (most recent call last):
File "
TypeError: bad operand type for abs(): 'str'
while comparing The function cmp(x, y) requires two parameters. If x
>>> cmp(1 , 2)
-1
>>> cmp(2, 1)
1
>>> cmp(3, 3)
0
Python’s built-in common functions also include data type conversion functions , for example, the int() function can convert other data types to integers:
>>> int('123')
123
>>> int(12.34)
12
str() The function converts other types into str:
>>> str(123)
'123'
>>> str(1.23)
'1.23'
Write the function:
in In Python, to define a function, use the def statement, write the function name, parentheses, parameters in the parentheses, and colon:, then write the function body in the indented block, and use the return statement to return the return value of the function.
We take as an example a custom my_abs function that finds the absolute value:
def my_abs(x):
if When the statement is executed, once return is executed, the function will be executed and the result will be returned. Therefore, very complex logic can be implemented inside the function through conditional judgment and looping.
If there is no return statement, the result will be returned after the function is executed, but the result will be None.
def move(x, y, step, angle):
nx = x + step * math.cos(angle)ny = y - step * math.sin(angle)
return nx, ny
So we can get the return value at the same time:
>>> x, y = move(100, 100, 60, math.pi / 6)
>>> print x, y
But in fact this is just an illusion, the Python function still returns a single value:
>>> r = move(100, 100, 60, math.pi / 6)
>>> print r
Use print to print the return result. It turns out that the return value is a tuple!
However, in terms of syntax, parentheses can be omitted when returning a tuple, and multiple variables can receive a tuple at the same time and assign corresponding values according to position. Therefore, Python's function returning multiple values actually returns a tuple, but it is written more convenient.
if n== 1: u Return 1
Return n * Fact (n -1)
Be careful to prevent stack overflow when using recursive functions. In computers, function calls are implemented through the data structure of the stack. Whenever a function call is entered, a stack frame is added to the stack. Whenever a function returns, a stack frame is subtracted from the stack. Since the size of the stack is not infinite, too many recursive calls will cause stack overflow. You can try calculating fact(10000).
The definition of function move(n, a, b, c) is to move n disks from a to c with the help of b.
Reference code:
def move(n, a, b, c):
if n ==1:
print a, '-->', c
return
move(n-1, a, c , b)
print a, '-->', c
move(n-1, b, a, c)
move(4, 'A', 'B', 'C')
The way to solve recursive call stack overflow is through tail recursion optimization. In fact, the effects of tail recursion and loops are the same, so it is okay to regard loops as a special tail recursive function.
Tail recursion means that when the function returns, it calls itself, and the return statement cannot contain expressions. In this way, the compiler or interpreter can optimize tail recursion so that the recursion itself only occupies one stack frame no matter how many times it is called, and stack overflow will not occur.
The fact(n) function above introduces a multiplication expression due to return n * fact(n - 1), so it is not tail recursive. To change to tail recursion, you need a little more code, mainly to pass the product of each step into the recursive function:
def fact(n):
return fact_iter(n, 1)def fact_iter(num, product) :
if num == 1: return product return fact_iter(num - 1, num * product)
You can see that return fact_iter(num - 1, num * product) only returns the recursive function itself, num - 1 and num * product will be calculated before the function call and does not affect the function call. The call to fact_iter(5, 1) corresponding to
fact(5) is as follows:
===> fact_iter(5, 1)
===> fact_iter(4, 5)
===> fact_iter (3, 20)
===> fact_iter(2, 60)
===> fact_iter(1, 120)
===> 120
When making tail recursive calls, if optimization is done, the stack Will not grow, so no matter how many times it is called, it will not cause the stack to overflow.
Unfortunately, most programming languages are not optimized for tail recursion, and the Python interpreter is not optimized either. Therefore, even if the above fact(n) function is changed to tail recursion, it will cause stack overflow.
Define default parameters:
When defining a function, you can also have default parameters.
For example, the int() function that comes with Python actually has two parameters. We can pass either one parameter or two parameters:
>>> int('123')
123
>>> int('123', 8)
83
int() The second parameter of the function is the conversion base. If it is not passed, the default is decimal (base=10). If it is passed, Just use the parameters passed in.
It can be seen that the default parameters of the function are used to simplify the call. You only need to pass in the necessary parameters. But when needed, additional parameters can be passed in to override the default parameter values.
Let’s define a function that calculates x raised to the power of N:
def power(x, n):
s = 1
while n > 0:
n = n - 1
s = s * x
return s
Assuming that the number of squares is calculated the most, we can set the default value of n to 2:
def power(x, n=2):
s = 1
while n > 0:
n = n-1
The parameters are matched in order from left to right, so the default parameters can only be defined after the required parameters:
# OK:def fn1(a, b=1, c=2):
pass
First define a function, pass in a list, add an END and return:
L.append('END') return L
The results seem good when you call it normally:
>>> add_end([1, 2, 3])[1, 2, 3, 'END']>>> add_end( ['x', 'y', 'z'])['x', 'y', 'z', 'END']
>>> add_end()['END']
However, when add_end() is called again, the result is wrong:
>>> add_end()['END', 'END ']>>> add_end()['END', 'END', 'END']
Many beginners are confused. The default parameter is [], but the function seems to "remember" the list after adding 'END' last time.
The reason is explained as follows:
When the Python function is defined, the value of the default parameter L is calculated, that is, [], because the default parameter L is also a variable, which points to the object []. Every time the function is called, If the content of L is changed, the content of the default parameter will change the next time it is called, and it will no longer be [] when the function was defined.
So, when defining default parameters, you should keep one thing in mind: the default parameters must point to immutable objects!
To modify the above example, we can use the immutable object None to implement:
def add_end(L=None):
if L is None:
L = []
L.append('END') return L
Now, no matter how many times you call it, there will be no problem:
>>> add_end()['END']>>> add_end()['END']
Why design immutable objects like str and None? Because once an immutable object is created, the data inside the object cannot be modified, which reduces errors caused by modifying data. In addition, since the object does not change, there is no need to lock the object when reading it simultaneously in a multi-tasking environment, and there is no problem at all when reading it at the same time. When we write a program, if we can design an immutable object, then try to design it as an immutable object.
Define variable parameters:
If we want a function to accept any number of parameters, we can define a variable parameter:
def fn(*args):
print args
variable There is an * in front of the parameter name. We can pass in 0, 1 or more parameters to the variable parameters:
>>> fn()
()
>>> fn( 'a')
('a',)
>>> fn('a', 'b')
('a', 'b')
>>> fn('a' , 'b', 'c')
('a', 'b', 'c')
The Python interpreter will assemble the incoming set of parameters into a tuple and pass it to the variable parameter, so , inside the function, just treat the variable args directly as a tuple.
Keyword parameters:
Variable parameters allow you to pass in 0 or any number of parameters. These variable parameters are automatically assembled into a tuple when the function is called. Keyword parameters allow you to pass in 0 or any number of parameters containing parameter names. These keyword parameters are automatically assembled into a dict inside the function. Please see the example:
def person(name, age, **kw):
print('name:', name, 'age:', age, 'other:', kw)
function person except required In addition to the parameters name and age, it also accepts the keyword parameter kw. When calling this function, you can only pass in the required parameters:
>>> person('Michael', 30)
name: Michael age: 30 other: {}
You can also pass in any number Number of keyword parameters:
>>> person('Bob', 35, city='Beijing')
name: Bob age: 35 other: {'city': 'Beijing'}>> > person('Adam', 45, gender='M', job='Engineer')
name: Adam age: 45 other: {'gender': 'M', 'job': 'Engineer'}
What are keyword parameters used for? It can extend the function's functionality. For example, in the person function, we are guaranteed to receive the two parameters name and age, but if the caller is willing to provide more parameters, we can also receive them. Imagine you are doing a user registration function. Except for the user name and age, which are required, everything else is optional. Using keyword parameters to define this function can meet the registration needs.
Named keyword parameters:
For keyword parameters, the caller of the function can pass in any unlimited keyword parameters. As for what is passed in, you need to pass kw check inside the function.
Still taking the person() function as an example, we want to check whether there are city and job parameters:
def person(name, age, **kw):
if 'city' in kw: # There is a city parameter
pass
if 'job' in kw:# Have a job parameter
pass
proprint ('name:', name, 'age:', Age, 'Other:', kw)
but the caller can still pass in unlimited restrictions. Keyword parameters:
>>> person('Jack', 24, city='Beijing', addr='Chaoyang', zipcode=123456)
If you want to limit the name of the keyword parameter, just Named keyword parameters can be used, for example, only city and job are received as keyword parameters. The function defined in this way is as follows:
def person(name, age, *, city, job):
print(name, age, city, job)
is different from the keyword parameter **kw, named keyword Parameters require a special delimiter *, and parameters following * are treated as named keyword parameters.
The calling method is as follows:
>>> person('Jack', 24, city='Beijing', job='Engineer')
Jack 24 Beijing Engineer
Named keyword parameters must be passed in the parameter name , which is different from positional parameters. If no parameter name is passed in, the call will report an error:
>>> person('Jack', 24, 'Beijing', 'Engineer')
Traceback (most recent call last):
File "
Due to the lack of parameter names city and job when calling, the Python interpreter treats these 4 parameters as positional parameters , but the person() function only accepts 2 positional parameters.
Named keyword arguments can have default values, simplifying calls:
def person(name, age, *, city='Beijing', job):
print(name, age, city, job)
Since the named keyword parameter city has a default value, you do not need to pass in the city parameter when calling:
>>> person('Jack', 24, job='Engineer')
Jack 24 Beijing Engineer
Use When naming keyword parameters, pay special attention to the fact that * is not a parameter, but a special delimiter. If * is missing, the Python interpreter will not recognize positional arguments and named keyword arguments:
def person(name, age, city, job):
#With * missing, city and job are treated as positional arguments
pass
Parameter combination:
When defining a function in Python, you can use required parameters, default parameters, variable parameters, keyword parameters and named keyword parameters. These five parameters can be used in combination, except that variable parameters cannot be combined with named keys. Word parameter mix. However, please note that the order of parameter definitions must be: required parameters, default parameters, variadic parameters/named keyword parameters, and keyword parameters.
For example, define a function that contains the above parameters:
def f1(a, b, c=0, *args, **kw):
print('a =', a, 'b =', b , 'c =', c, 'args =', args, 'kw =', kw)def f2(a, b, c=0, *, d, **kw):
print('a =', a, 'b =', b, 'c =', c, 'd =', d, 'kw =', kw)
When a function is called, the Python interpreter automatically interprets it according to the parameter position and name. The corresponding parameters are passed in.
>>> f1(1, 2)
a = 1 b = 2 c = 0 args = () kw = {}>>> f1(1, 2, c=3)
a = 1 b = 2 c = 3 args = () kw = {}>>> f1(1, 2, 3, 'a', 'b')
a = 1 b = 2 c = 3 args = ('a', 'b') kw = {}>>> f1(1, 2, 3, 'a', 'b', x=99)
a = 1 b = 2 c = 3 args = ('a', 'b') kw = {'x': 99}>>> f2(1, 2, d=99, ext=None)
a = 1 b = 2 c = 0 d = 99 kw = {'ext': None}
The most amazing thing is that through a tuple and dict, you can also call the above function:
>>> args = (1, 2, 3, 4) >>> kw = {'d': 99, 'x': '#'}>>> f1(*args, **kw)
a = 1 b = 2 c = 3 args = (4,) kw = {'d': 99, 'x': '#'}>>> args = (1, 2, 3)>>> kw = {'d': 88 , 'x': '#'}>>> f2(*args, **kw)
a = 1 b = 2 c = 3 d = 88 kw = {'x': '#'}
So, for any function, you can call it through a form like func(*args, **kw), no matter how its parameters are defined.
Summary
Python's functions have a very flexible parameter form, which can not only implement simple calls, but also pass in very complex parameters.
The default parameters must use immutable objects. If they are variable objects, there will be logic errors when the program is running!
Pay attention to the syntax for defining variable parameters and keyword parameters:
*args is a variable parameter, args receives a tuple;
**kw is a keyword parameter, and kw receives a dict.
And the syntax of how to pass in variable parameters and keyword parameters when calling a function:
Variable parameters can be passed in directly: func(1, 2, 3), or you can assemble a list or tuple first, and then pass * args is passed in: func(*(1, 2, 3));
Keyword parameters can be passed in directly: func(a=1, b=2), or you can assemble the dict first and then pass it through **kw Enter: func(**{'a': 1, 'b': 2}).
Using *args and **kw is the idiom of Python. Of course, other parameter names can also be used, but it is best to use the idiom.
Named keyword parameters are used to limit the parameter names that the caller can pass in and provide default values.
Don’t forget to write the delimiter * when defining named keyword parameters, otherwise positional parameters will be defined.