在循环中从列表中删除项目

1 投票
4 回答
580 浏览
提问于 2025-04-17 00:30

我已经尝试了很长一段时间,想找个方法来遍历一个列表,并删除我当前正在处理的项目。但我似乎无法按我想要的方式实现。它只循环了一次,而我希望它能循环两次。当我去掉删除那一行时,它就能循环两次。

a = [0, 1]
for i in a:
    z = a
    print z.remove(i)

输出结果:

[1]

我原本期待的输出结果:

[1] 
[0]

4 个回答

2

问题在于你在用 remove 修改了 a,所以循环会结束,因为现在的索引已经超过了它的末尾。

8

你在遍历这个列表的时候同时在修改它——z = a 并不是在复制,而是让 z 指向和 a 一样的地方。

你可以试试

for i in a[:]:          # slicing a list makes a copy
    print i             # remove doesn't return the item so print it here
    a.remove(i)         # remove the item from the original list

或者

while a:                # while the list is not empty
    print a.pop(0)      # remove the first item from the list

如果你不需要一个明确的循环,你可以用列表推导式来删除符合条件的项:

a = [i for i in a if i] # remove all items that evaluate to false
a = [i for i in a if condition(i)] # remove items where the condition is False
3

在循环遍历一个列表的时候,直接修改这个列表是不太好的做法。你应该先创建这个列表的一个副本:

oldlist = ['a', 'b', 'spam', 'c']
newlist = [x for x in oldlist if x != 'spam']

如果你想修改原来的列表,可以通过切片赋值的方式把副本的内容写回去:

oldlist[:] = [x for x in oldlist if x != 'spam']

† 之所以这样做不好,主要是因为在遍历的过程中,如果列表发生了变化,迭代器的行为会变得很复杂。想象一下,如果你删除了当前项,迭代器应该指向原列表中的下一个项,还是修改后的列表中的下一个项呢?如果你的操作是删除当前项的前一个(或者后一个)项,又该如何处理呢?

撰写回答