函数function
是可向调用者返回某个值的一组语句,他可以接收若干参数并在函数体中使用。
函数定义
函数定义是一条可执行语句。函数定义语句会在当前局部命名空间中,将函数名称与函数对象绑定。此函数对象包含对当前全局命名空间的引用,作为函数被调用时所使用的全局命名空间。
函数定义时函数体不会执行,只有函数调用时函数体才会。
于Python而言,定义一个函数、类,与定义一个实例并无本质区别。在函数、类内定义函数、类,只是新增了一个局部对象。若是将Python执行上下文理解为一个散列表,而Python所有对象都是基于object(PyObject)
的类的实例。上下文只是将这些名字与实例关联起来的容器。如类type(PyTypeObject)、函数function(PyFunctionObject)等。
装饰
函数可以被若干个装饰器表达式所包装。当执行函数定义时,在该作用域对装饰器表达式求值,返回一个可调用对象绑定到函数名称。多个装饰器将以嵌套方式求值。
@f1(arg)
@f2
def func(): pass
形同
def func(): pass
func = f1(arg)(f2(func))
但前者,没有原始函数绑定到名称func
的中间过程。
默认形参值
形参 = 表达式
形式的参数具有默认形参值,表达式求值结果即其默认值。默认形参值会在执行函数定义时,按从左往右顺序求值。
表达式仅在函数定义时求值一次,此值将在之后的函数调用过程中持续使用。若表达式求值结果为一可变对象,则其修改将会影响后续的函数调用过程。
若欲使函数具有默认形参值,又不希望被可变对象性质所影响,则可将之默认值置为None
,并进行判断。
def whats_on_the_telly(penguin=None):if penguin is None:penguin = []penguin.append("property of the zoo")return penguin
参数 argument
参数是函数调用时实际传入的值。根据传参方式不同,可将参数分为一下两种:
- 关键字参数
在函数调用时,前面带有标识符,或具有前缀
**
的字典里的值。如:
complex(real=3, imag=5)
complex(**{'real': 3, 'imag': 5}) # 参数是 real=3, imag=5
- 位置参数
关键字参数之外的参数。于参数列表开头,或具有前缀
*
的可迭代对象里的值。如:
complex(3, 5)
complex(*(3, 5)) # 参数是 3, 5
形参 parameter
形参是函数定义中的命名实体,代表函数可以接受的参数argument
。它可以是以下几种形式:
- 位置或关键字形参
默认形参类型,可以通过位置,也可以通过关键字传入的参数。如
foo
和bar
:
def func(foo, bar=None): ...
- 仅限位置形参
在部分参数列表之后,插入
/
参数,表示只能通过指定位置传入。如posonly1
和posonly2
:
def func(posonly1, posonly2, /, positional_or_keyword): ...
- 仅限关键字形参
在部分可变位置形参之前,插入
*
参数,表示只能通过指定关键字传入。如kw_only1
和kw_only2
:
def func(arg, *, kw_only1, kw_only2): ...
- 可变位置形参
在其他位置参数之后的参数名称前添加
*
,表示任意数量位置参数。如args
:
def func(arg1, arg2, *args): ...
- 可变关键字形参
在其他关键字参数之后的参数名称前添加
**
,表示任意数量关键字形参。如kwargs
:
def func(*args, **kwargs): ...