尝试将所有5个变为100个。我知道你应该使用列表理解,但为什么这不起作用?有人能从理论上解释一下吗?谢谢。
d = [5,1,1,1,5]
def f1(seq):
for i in seq:
if i==5:
i = 100
return seq
print (f1(d))
答案 0 :(得分:4)
这一行:
i = 100
提供本地变量i
,该变量最初在seq
中分配了该值100
。
要更改序列中的值,您可以执行以下操作:
for index, object in enumerate(seq):
if object == 5:
seq[index] = 100
枚举每次在序列上调用时返回两个对象,索引作为数字,以及对象本身。
请参阅列表上的文档和(Python 2)enumerate。
你也可以写:
for index in range(len(seq)):
if seq[index] == 5:
seq[index] = 100
您可能更喜欢哪种,但有时候认为不太干净。
答案 1 :(得分:2)
Python赋值运算符将值绑定到名称。您的循环for i in seq
会在每次迭代时将seq
的值绑定到本地名称i
。然后i = 100
将值100
绑定到i
。这不会影响原始序列,并且在循环的下一次迭代中将再次更改绑定。
您可以使用enumerate
列出索引以及seq
的值并以这种方式执行绑定:
def f1(seq):
for n, i in enumerate(seq):
if i == 5:
seq[n] = 100
return seq
更简单的可能是迭代索引:
def f2(seq):
for n in range(len(seq)):
if seq[n] == 5:
seq[n] = 100
return seq
上面显示的选项将原位修改序列。除方便之外,您无需退回。还可以选择基于旧序列创建新序列。然后,您可以重新绑定变量d
以指向新序列并删除旧序列。
最简单且可能最恐怖的方法是使用列表理解:
d = [5, 1, 1, 1, 5]
d = [100 if x == 5 else x for x in d]
您还可以使用map
:
d = list(map(lambda x: 100 if x == 5 else x, d))
map
的输出是一个生成器,所以我将它包装在list
中以保留相同的输出类型。这在Python 2中是不必要的,其中map
已经返回一个列表。
答案 2 :(得分:1)
采用以下示例:
def f1(seq):
for i in seq:
if i==5:
i = 100
# at this point (assuming i was 5), i = 100 but seq is still [3,5,7]
# because i is not a reference to the item but the value *copied* from the list
...
f1([3,5,7])
您可以循环索引并在列表中的该索引处设置值:
d = [5,1,1,1,5]
def f1(seq):
for i in range(len(seq)):
if seq[i]==5:
seq[i] = 100
return seq
print(f1(d))
# [100,1,1,1,100]
答案 3 :(得分:1)
您应该更新列表中的元素,如:
def f1(seq):
for i in range(len(seq)): # run through the indexes of the list
if seq[i]==5: # check whether seq at index i is 5
seq[i] = 100 # update the list at the same index to 100
return seq
i
是在循环内创建的新变量,因此它与列表中的元素不同。
注意:
请注意,list是一个可变对象,因此即使在函数外部,更改函数内的seq也会影响列表。
您可以在here
中阅读有关mutable和immutable的更多信息