之前Q群里有人问了一个问题:如何移除列表s中的满足某个条件的元素? 很自然地写了一个
for x in s:
if 满足条件:
s.remove(x)
但是运行时发现s中的某些元素被跳过了,实现不了他想要的功能。
我们下面举一个具体的例子说明为什么会这样。比如现在想删除列表s中的偶数: 按照文章开头的写法:
s = [1,2,4,3]
for x in s:
if x % 2 == 0:
s.remove(x)
print(s) # [1, 4, 3]
运行发现,元素2被删除了,但是元素4被跳过了,没有删除。这是因为删除一个元素后,该元素所在位置会空出来,右边的元素会左移填上这个空缺:
当指到元素“2”的时候,发现是偶数,删除2,右边的4,3会左移。但指针不会左移。指针下一次移动就会移动到3,4就被跳过了。
1、 遍历s的副本(通过切片或其他方法创建副本),修改s:
s = [1,2,4,3]
for x in s[:]:
if x % 2 == 0:
s.remove(x)
print(s)
2、列表推导 直接生成一个需要的新列表。
s = [1,2,4,3]
s = [x for x in s if x%2 != 0]
一个技巧是分配给s的切片,时间上会更高效。
s = [1,2,4,3]
s[:] = [x for x in s if x%2 != 0]
3、利用itertools的filterfalse
from itertools import filterfalse
def even(x):
return x % 2 == 0
s = [1,2,4,3]
s[:] = filterfalse(even,s)
print(s)
方法2、3 来源:Python 10 Python Basics You Should Know! 作者 Python Engineer: