Python 默认列表参数不为';t重置

Python 默认列表参数不为';t重置,python,Python,考虑以下代码: def f(a=[]): print(a) a += [1] f() f() f() 哪个输出 [] [1] [1,1] 这种行为似乎很奇怪。参数a是否应在每次函数运行时重置为[]? 当参数为整数时,我得到预期的行为: def f(a=1): print(a) a += 1 f() f() f() 输出 1 1 1 我知道列表是可变的,整数不是,但我不知道这在这里是否重要。 谢谢。不。可变对象初始值设定项执行此操作是Python的一个缺点。更好的模式是

考虑以下代码:

def f(a=[]):
  print(a)
  a += [1]

f()
f()
f()
哪个输出

[]
[1]
[1,1]
这种行为似乎很奇怪。参数
a
是否应在每次函数运行时重置为
[]
? 当参数为整数时,我得到预期的行为:

def f(a=1):
  print(a)
  a += 1

f()
f()
f()
输出

1
1
1
我知道列表是可变的,整数不是,但我不知道这在这里是否重要。
谢谢。

不。可变对象初始值设定项执行此操作是Python的一个缺点。更好的模式是使用
None
并在方法体中设置初始值:

def f(a=None):
  if a is None:  
    a = []
  print(a)
  a += [1]

如果您使用,它会提供一个警告
危险的默认值(W0102)

这在Python中有点困难。默认参数不仅设置默认值,还捕获对象。也就是说,正如您所看到的,默认参数是一个特定的列表对象,该对象恰好初始化为空。您可能认为您可以这样做:

def f(a=[]):
    a = a[:]
但如果你这样做了,那么任何时候有人进入一个列表,你都会复制一份,而你所做的更改将不会出现在原始列表中。这有时是一个很好的选择:

def f(a=None):
    if not a:
        a = []

看起来你的问题以前被问过并回答过。欢迎加入,但它可能会作为副本关闭。这不是你的错,但这个问题在Python中很常见,以前也有人问过,Stackoverflow试图避免重复。在任何情况下,不管你是不是被愚弄了,你都希望找到有用的答案。