【问题标题】:Default values for arguments [duplicate]参数的默认值 [重复]
【发布时间】:2011-08-04 08:59:48
【问题描述】:

可能重复:
“Least Astonishment” in Python: The Mutable Default Argument

考虑以下函数:

def foo(L = []):
  L.append(1)
  print L

每次我调用 foo 时,它都会打印一个新列表,其中包含比上次更多的元素,例如:

>>> foo()
[1]
>>> foo()
[1, 1]
>>> foo()
[1, 1, 1]

现在考虑以下函数:

def goo(a = 0):
  a += 1
  print a

多次调用,得到如下图:

>>> goo()
1
>>> goo()
1
>>> goo()
1

即它不会在每次调用时打印更大的值。

这种看似不一致的行为背后的原因是什么?
另外,如何证明第一个示例中的反直觉行为是合理的,为什么函数在调用之间保持状态?

【问题讨论】:

  • 以及同一问题的许多其他答案。
  • 为什么我们会突然无数次地收到这个问题?

标签: python function default-arguments


【解决方案1】:

默认参数在定义函数时计算一次。 所以每次调用函数时都会得到相同的list 对象。

每次调用第二个函数时,您也会得到相同的0 对象,但由于int 是不可变的,当您添加1 作为新对象时需要绑定到一个

>>> def foo(L = []):
...   print id(L)
...   L.append(1)
...   print id(L)
...   print L
... 
>>> foo()
3077669452
3077669452
[1]
>>> foo()
3077669452
3077669452
[1, 1]
>>> foo()
3077669452
3077669452
[1, 1, 1]

>>> def foo(a=0):
...   print id(a)
...   a+=1
...   print id(a)
...   print a
... 
>>> foo()
165989788
165989776
1
>>> foo()
165989788
165989776
1
>>> foo()
165989788
165989776
1

【讨论】:

  • 这并不能完全回答我的问题 - 我不明白为什么第二个示例(带有整数参数)会这样工作。
  • > 每次调用第二个函数时,你也会得到相同的 0 对象——那为什么每次调用第一个函数时我不能得到相同的 [] 对象呢?
  • @Grigory:整数是不可变的,some_int += ... 创建一个新整数而不是修改some_inta 以相同的 0 开头,每次调用函数时都没有给出参数,你只需将 a 更改为指向 0 + 1
  • 事实上,每次调用第一个函数时,您都会得到相同的对象。这就是它“记住”之前内容的原因。
  • @delnan 谢谢,这解释了一切。
猜你喜欢
  • 1970-01-01
  • 1970-01-01
  • 1970-01-01
  • 1970-01-01
  • 2013-02-14
  • 2017-04-14
  • 2011-09-23
  • 2014-02-10
  • 1970-01-01
相关资源
最近更新 更多