码迷,mamicode.com
首页 > 编程语言 > 详细

python函数默认参数为可变对象的理解

时间:2018-08-20 14:37:40      阅读:202      评论:0      收藏:0      [点我收藏+]

标签:code   赋值   返回   数列   close   代码执行   情况   可变对象   如何   

1.代码在执行的过程中,遇到函数定义,初始化函数生成存储函数名,默认参数初识值,函数地址的函数对象。

2.代码执行不在初始化函数,而是直接执行函数体。

技术分享图片代码实例

 

这要从函数的特性说起,在 Python 中,函数是第一类对象(function is the first class object),换而言之,函数也是对象,跟整数、字符串一样可以赋值给变量、当做参数传递、还可以作为返回值。函数也有自己的属性,比如函数的名字、函数的默认参数列表。

# 函数的名字

>>> func.__name__

  ‘func‘

  # 函数的默认参数列表

>>> func.__defaults__

  ([ 1, 1, 1, 1, 1], 1)

def是一条可执行语句,Python 解释器执行 def 语句时,就会在内存中就创建了一个函数对象(此时,函数里面的代码逻辑并不会执行,因为还没调用嘛),在全局命名空间,有一个函数名(变量叫 func)会指向该函数对象,记住,至始至终,不管该函数调用多少次,函数对象只有一个,就是function object,不会因为调用多次而出现多个函数对象。

技术分享图片

函数对象生成之后,它的属性:名字和默认参数列表都将初始化完成。

技术分享图片

初始化完成时,属性 __default__ 中的第一个默认参数 numbers 指向一个空列表。

当函数第一次被调用时,就是第一次执行 func()时,开始执行函数里面的逻辑代码(此时函数不再需要初始化了),代码逻辑就是往numbers中添加一个值为1的元素

技术分享图片

第二次调用 func(),继续往numbers中添加一个元素

技术分享图片

第三次、四次依此类推。

所以现在你应该明白为什么调用同一个函数,返回值确每次都不一样了吧。因为他们共享的是同一个列表(numbers)对象,只是每调用一次就往该列表中增加了一个元素

如果我们显示地指定 numbers 参数,结果截然不同。

>>> func(numbers=[ 10, 11])

[ 10, 11, 1]

技术分享图片

因为numbers被重新赋值了,它不再指向原来初始化时的那个列表了,而是指向了我们传递过去的那个新列表对象,因此返回值变成了 [10, 11, 1]

那么我们应该如何避免前面那种情况发生呢?就是不要用可变对象作为参数的默认值。

正确方式:

>>> deffunc(numbers=None, num=1):

... ifnumbers isNone:

... numbers = [num]

... else:

... numbers.append(num)

... returnnumbers

...

 

 

python函数默认参数为可变对象的理解

标签:code   赋值   返回   数列   close   代码执行   情况   可变对象   如何   

原文地址:https://www.cnblogs.com/wuchenggong/p/9505119.html

(0)
(0)
   
举报
评论 一句话评论(0
登录后才能评论!
© 2014 mamicode.com 版权所有  联系我们:gaon5@hotmail.com
迷上了代码!