Python 当传递给函数时,列表会发生什么变化?
我试图理解当列表作为参数传递给函数时是如何处理的。所以我做了以下几点: 我初始化了一个列表:Python 当传递给函数时,列表会发生什么变化?,python,list,function,Python,List,Function,我试图理解当列表作为参数传递给函数时是如何处理的。所以我做了以下几点: 我初始化了一个列表: ll = [1,2,3,4] 并定义一个函数: def Foo(ar): ar += [11] Foo(ll) 我将列表传递给函数: def Foo(ar): ar += [11] Foo(ll) 当我打印它时,我得到: print ll # [1, 2, 3, 4, 11] #case(1) 到目前为止还不错 现在我修改了该函数,以便重置列表,使其仅包含一个元素: def
ll = [1,2,3,4]
并定义一个函数:
def Foo(ar):
ar += [11]
Foo(ll)
我将列表传递给函数:
def Foo(ar):
ar += [11]
Foo(ll)
当我打印它时,我得到:
print ll # [1, 2, 3, 4, 11] #case(1)
到目前为止还不错
现在我修改了该函数,以便重置列表,使其仅包含一个元素:
def Foo(ar):
ar = [11]
我回忆起语法:
Foo(ll)
当我重印它时,它产生了相同的列表:
print ll # [1, 2, 3, 4] # case(2)
我以为名单是作为参考而通过的;因此,无论我们对函数中的列表做什么,都将始终更改从主程序传递的原始函数。因此,对于案例(2),我期望得到以下结果:
print ll # [11] # case(2) expected result
我在这里遗漏了什么吗?
ar+=[11]
不是一个作业。这是一个方法调用(被调用的方法是:\uuuuidd\uuuu
)。当Python执行该行时,它调用该方法,然后将ar
赋值给结果。列表
的\uu\uu iadd
方法修改当前的列表
ar=[11]
是一个赋值,因此它只需更改本地名称ar
的值。但是函数中的ar
名称与ll
变量的值之间没有联系
您可能需要以下内容:
ar[:] = [11]
像
+=
这样的扩充赋值做了一些正常=
赋值不能做的事情。当您指定一个名称时,如下所示:
ar = [11]
这是对ar
名称的操作。前面提到的列表对象ar
没有改变,因此当您在函数外部执行print ll
时,您会看到原始列表
当你这样做的时候
ar += [11]
这不完全等同于
ar = ar + [11]
如果您这样做了,
ar=ar+[11]
,ll
将保持不变。但是,+=
请求,如果可能,ar
引用的列表应该通过修改其自身的状态来执行操作,而不是通过创建新列表。由于列表是可变的,因此列表会修改自身以具有一个新的11
元素,并且此更改通过ll
变量可见。您必须在对象和对象名称之间进行区分。Python中的列表是可变对象,因此只要有对它的引用,就可以对其进行更改
名称只是对对象的引用。请记住,从技术上讲,Python中没有变量,只有名称和对象,对象与名称绑定
因此,考虑到这一点,让我们看看您的代码:
def Foo1(ar):
ar += [11]
此函数获取列表,将其绑定到本地名称ar
,然后修改列表,添加新值
但是,其他代码:
def Foo2(ar):
ar = [11]
此函数获取一个绑定到ar
名称的列表,然后使用一个值将名称ar
重新绑定到一个新列表。在这个函数中,原始对象是未修改的和模糊的
然后,当您这样做时:
a = [1,2,3]
然后打电话:
Foo1(a)
这会修改列表并添加新值,但:
Foo2(a)
对a
的值不执行任何操作
如果要编写一个函数,用另一个函数替换列表中的所有内容,可以使用以下函数:
def Foo3(a):
a[:] = [11]
此代码不会重新绑定a
,而是通过用新列表替换内容来修改列表
为了进一步说明我的观点,请看以下示例:
a = []
b = []
c = a
a.append(1)
b.append(2)
c.append(3)
print a
print b
print c
它将打印:
[1, 3]
[2]
[1, 3]
你能告诉我为什么吗?
ar=[11]
将名称分配给一个完全不同的对象。如果您想替换列表的全部内容,请尝试ar[:]=[11]
。我发现您选择的名称和值(ll
和11
)令人不安……我很抱歉选择了名称和值。严格来说,ar+=[11]
实际上仍然是一项任务;它需要用于ar=(1,2,3)之类的东西;ar+=(11,)
工作。@user2357112你说得对,我太简单了。修正。谢谢你的帮助。我想我现在明白了。这才是我真正需要的:ar[:]=[11]是因为a&c的名字现在用来指同一个对象吗?谢谢你的解释。谢谢你的解释!