Python中的本地和全局列表

时间:2019-02-12 08:25:04

标签: python python-3.x list global-variables local-variables

由于我是python新手,请帮助我 当我调用此函数时,list1的原始值会更改

def mystery(list1):
  list1[0] , list1[1] = list1[1], list1[0]

list1 = [7,82,44,23,11]
mystery(list1)
print(list1) #prints [82, 7, 44, 23, 11]

它如何改变全局list1的值 如果我将功能更改为

def mystery(list1):
  list1 = list1 + list1[2:5]

然后我得到的是list1的全局值,而不是更新的值。

5 个答案:

答案 0 :(得分:1)

列表是python中的可变对象,因此,如果要传递给函数列表,则对函数内部的列表所做的所有更改都会在全球/全球范围内反映出来

如果将可变对象传递给方法,则该方法将获取对该对象的引用,并且可以对其进行更改,但如果您在该方法中重新绑定该引用,则外部范围对此一无所知,完成后,外部参考仍将指向原始对象。

如果您将不可变的对象传递给方法,则仍然无法重新绑定外部引用,甚至无法使对象发生突变。[more details here]

答案 1 :(得分:1)

也许只是返回列表?

def mystery(list1):
    return list1 + list1[2:5]

list1 = [7,82,44,23,11]
list1 = mystery(list1)
print(list1)

答案 2 :(得分:1)

list1发生变化的原因是因为您实际上是在函数内部修改list对象。

它确实与全局/局部变量无关,如果您将函数内部的参数重命名为其他名称,并且仍然传递给list1,则list1将被修改。

如果要返回新列表,则需要首先创建列表的副本,可以通过多种方法进行。 list(list1)是一种方法。然后return在函数末尾的列表。

如果我了解您的问题,实际上想将更多值附加到传入列表中,请使用list1.append(...)添加到列表的末尾。

由于您是在修改列表本身,因此它将在更大的范围内更改。

但是它仍然没有使用全局作用域,因为您只是在本地作用域中使用了具有相同名称的var。

答案 3 :(得分:0)

在python中,将值分配给a = 5之类的变量意味着您正在内存中为值5创建一个对象。现在a是指向该对象的链接,该对象拥有5个(按Layman的说法) )。如果现在更改a,例如说a = "something else",这将在内存中的其他位置为字符串"something else"创建一个新对象,现在a指向该对象。这就是为什么要更改python变量的数据类型的原因。

当您将某些东西传递给python函数时,该链接就是传递的链接。因此,当您调用mystery(list1)时,将传递到list1的原始链接。因此,更改list1中的元素意味着您要为原始list1中的特定元素分配一个新值。在这种情况下,无论您在函数mystery()内还是外部,都将使用创建的原始链接访问list1中的元素来更改它。更改发生在list1内部; list1没有得到重新分配。

但是,当您在函数list1 = "something new"中执行mystery()时,您将在函数内部创建一个新变量list1,该变量是该函数的局部变量。您没有更改原始的list1

答案 4 :(得分:0)

将可变对象传递给函数,然后在函数内部修改对象将具有与直接修改对象相同的效果。

list1 = [1,2,3]

def func(list1):
    list1[0] = 5

>>>list1
[5,2,3]

这实际上与直接运行list1[0] = 5

相同

但是,如果将不可变对象传递给元组之类的函数,它将不支持项目分配TypeError: 'tuple' object does not support item assignment。因此,您需要构建一个新的不可变对象并返回它。

>>> tup1 = (1,2,3) # doing tup1[0] = 5 will cause TypeError
>>> tup2 = tup1 + (5,)
>>> tup2
(1, 2, 3, 5)

将其放入功能中,

>>> def func2(tup1):
        return tup1 + (5,)

>>> func2(tup1=(1,2,3))
(1, 2, 3, 5)