python tips - 注意函数参数的默认值-默认参数-可选参数

来源:互联网 发布:大数据平台架构师 编辑:程序博客网 时间:2024/05/17 06:49

且看如下例子:

复制代码
 
def f(a=[]):    a.append(0)    return aprint dir(f)for i in range(3):    print f()    print f.__defaults__
复制代码

结果:

复制代码
['__call__', '__class__', '__closure__', '__code__', '__defaults__', '__delattr__', '__dict__', '__doc__', '__format__', '__get__', '__getattribute__', '__globals__', '__hash__', '__init__', '__module__', '__name__', '__new__', '__reduce__', '__reduce_ex__', '__repr__', '__setattr__', '__sizeof__', '__str__', '__subclasshook__', 'func_closure', 'func_code', 'func_defaults', 'func_dict', 'func_doc', 'func_globals', 'func_name']([],)[0]([0],)[0, 0]([0, 0],)[0, 0, 0]
复制代码

函数参数的默认值会保存上次调用的修改么?

每运行一次,函数作为一个对象的内在属性的值发生了变化。导致每次运行的结果不一致

 

复制代码
def f(num=0):    num += 1    return numprint dir(f)for i in range(3):    print f.__defaults__    print f()
复制代码

结果:

复制代码
['__call__', '__class__', '__closure__', '__code__', '__defaults__', '__delattr__', '__dict__', '__doc__', '__format__', '__get__', '__getattribute__', '__globals__', '__hash__', '__init__', '__module__', '__name__', '__new__', '__reduce__', '__reduce_ex__', '__repr__', '__setattr__', '__sizeof__', '__str__', '__subclasshook__', 'func_closure', 'func_code', 'func_defaults', 'func_dict', 'func_doc', 'func_globals', 'func_name'](0,)1(0,)1(0,)1
复制代码

函数参数的默认值怎么又没有保存上次调用的修改呢?

 

参考:python tips - Python可变对象和不可变对象:http://www.cnblogs.com/congbo/archive/2012/11/20/2777031.html

使用可变参数作为默认值可能导致意料之外的行为。为了防止出现这种情况,最好使用None值,并且在后面加上检查代码,如示例1改为:

复制代码
def f(a=None):    if a is None:        a = []    a.append(0)    return a
 
复制代码

 

查阅Python manual有如下的说法:

Default parameter values are evaluated when the function definition is executed. This means that the expression is evaluated once, when the function is defined, and that that same “pre-computed” value is used for each call. This is especially important to understand when a default parameter is a mutable object, such as a list or a dictionary: if the function modifies the object (e.g. by appending an item to a list), the default value is in effect modified. This is generally not what was intended. A way around this is to use None as the default, and explicitly test for it in the body of the function, e.g.:


python中函数的默认值只会被执行一次,(和静态变量一样,静态变量初始化也是被执行一次)。Python可以通过函数的默认值来实现静态变量的功能。

0 0