我想做以下事情:
x = 1
y = 2
z = 3
l = [x,y,z]
for variable in l:
variable += 2
print x
print y
print z
不幸的是,当我在此块之后打印x,y和z时,值分别保持在1,2和3。
我查看了this相关问题,但那里的解决方案并没有解决我的问题。
是否有一种简洁有效的方法对多个变量执行相同的操作,就像我上面尝试过的那样?
P.S。我使用的是Python 2.6
答案 0 :(得分:9)
你不能像这样改变x,y,z。 x,y,z是整数,它们是不可变的。你需要制作新的变量。
x, y, z = (v + 2 for v in l)
答案 1 :(得分:2)
问题是variable
的范围是for
循环。
如果你要写
for variable in my_list:
variable += 2
print variable
你会看到你期望的价值。但是,一旦进入下一个for
循环迭代,变量将被遗忘并替换为下一个列表值。
您想要做的是:
for i in range(len(my_list)):
list[i] += 2
会产生你想要的效果。这是因为它是列表中的实际项目增加2,而不是for循环中的本地副本。
答案 2 :(得分:1)
查看map
。
x = 1
y = 2
z = 3
l = [x,y,z]
l = map(lambda x: x+2, l) # [3, 4, 5]
你基本上是"映射"一个列表到另一个列表,修改了lambda函数定义的每个元素。
答案 3 :(得分:1)
您可以使用列表推导尝试类似下面的内容,然后将返回的值分配给变量x
,y
,z
>>> x = 1
>>> y = 2
>>> z = 3
>>> lst = [x,y,z]
>>> [i+2 for i in lst]
[3, 4, 5]
>>> x, y, z = [i+2 for i in lst]
>>> x
3
>>> y
4
>>> z
5
如下面的评论中所述,请勿使用list
作为变量名称。 list
是用于创建列表的特殊函数。
答案 4 :(得分:1)
您可以使用列表理解:
print [variable+2 for variable in list]
'可变'在你的情况下是局部变量,一旦你退出for循环,它的范围就会减少。最好避免列表名称为list
,因为它是内置的
答案 5 :(得分:1)
通常最好将一堆你想要操作的东西存储在列表中
xyz = [1, 2, 3]
for i in range(len(xyz)):
xyz[i] += 2
有时(但你应该首先寻找其他方法)exec
是好的(但如果你在用户的控制下执行输入,要小心)
>>> x = 1
>>> y = 2
>>> z = 3
>>> for variable in ['x', 'y', 'z']:
... exec '{} += 2'.format(variable)
...
>>> x, y, z
(3, 4, 5)
答案 6 :(得分:1)
我还没有看到答案提及可变性与不变性,这是为什么你看到这个行为。它在Python中是一个非常重要的概念,因为它取代了"通过引用传递的概念" "传递价值"其他语言有。请参阅the documentation进行深入处理,但我会在此提供一个快速说明性示例。
在Python中,int
是不可变的。这意味着无法更改整数的值。另一方面,list
和dict
是可变的,这意味着它们可以被更改。
考虑以下两种情况:
x = (1,2,3,4,5)
for y in x:
y += 1
print x
打印:
(1, 2, 3, 4, 5)
这里我们尝试更新int
s,它们是不可变的。因此,在for
- 循环之后,x
保持不变。您可以认为在循环的每次迭代中,x
的当前条目被复制到y
,并且此副本被更改,而不是条目本身。现在让我们改变一个可变类型:
x = ([1], [2], [3], [4], [5])
for y in x:
y += [42]
print x
打印:
([1, 42], [2, 42], [3, 42], [4, 42], [5, 42])
我们发现x
的元素已经更改了。这正是因为x
的元素是列表,列表是可变的。
顺便说一句,您可能会注意到在两种情况下使用的容器都是一个元组,它是不可变的。你可以在元组中改变可变对象 - 没有问题 - 你只是不能改变元组本身及其包含的引用。
在完成所有这些之后,我仍然没有真正回答你的问题,但上面提到的答案是:你不应该单独存储这些对象,而是列在一个列表中。然后,给出的所有列表理解答案都是有意义的,并按照您的期望行事。
答案 7 :(得分:0)
目前尚不清楚是否要更改X,Y和Z的值或列表的内容。所以这里有一些选择:
# as pointed out by the comments this is a bad idea. It violates Pythonic principles
# and your outcomes may be less consistent than you would like
f = locals()
for n in ['x','y','z']:
f[n] += 2 # modifies the values of the variables
您还可能尝试获取包含所有更新值的新列表。对于那个使用地图:
l = map(lambda x: x+2, [x,y,z])
'''
you could also do:
l = [x,y,z]
l = map(lambda x: x+2, l)
'''
或者,您可能正在尝试更新l
列表的值:
l = [x,y,z]
for idx, val in enumerate(l):
l[idx] = val + 2