我有一个由大约20000个列表组成的列表。我使用每个列表的第三个元素作为标志。我想在这个列表上做一些操作,只要至少有一个元素的标志为0,就像这样:
my_list = [["a", "b", 0], ["c", "d", 0], ["e", "f", 0], .....]
在开始时,所有的标志都是0。我使用while循环来检查是否至少有一个元素的标志为0:
def check(list_):
for item in list_:
if item[2] == 0:
return True
return False
如果check(my_list)
返回True
,那么我将继续处理我的列表:
while check(my_list):
for item in my_list:
if condition:
item[2] = 1
else:
do_sth()
实际上,我想在迭代时删除my_list中的元素,但不允许在迭代时删除项。
原始my_list没有标志:
my_list = [["a", "b"], ["c", "d"], ["e", "f"], .....]
因为我不能在迭代时删除元素,所以我发明了这些标志。但是my_list
包含许多项,并且while
循环在每个for
循环中读取所有项,并且它消耗大量时间!你有什么意见建议?
发布于 2012-05-19 23:04:53
这里最好的答案是使用all()
,它是这种情况下的内置工具。我们将其与generator expression相结合,以干净高效地产生您想要的结果。例如:
>>> items = [[1, 2, 0], [1, 2, 0], [1, 2, 0]]
>>> all(flag == 0 for (_, _, flag) in items)
True
>>> items = [[1, 2, 0], [1, 2, 1], [1, 2, 0]]
>>> all(flag == 0 for (_, _, flag) in items)
False
请注意,all(flag == 0 for (_, _, flag) in items)
直接等同于all(item[2] == 0 for item in items)
,只是在这种情况下读起来更好一点。
对于过滤器示例,列表理解(当然,您可以在适当的地方使用生成器表达式):
>>> [x for x in items if x[2] == 0]
[[1, 2, 0], [1, 2, 0]]
如果您想检查至少有一个元素为0,更好的选择是使用可读性更好的any()
:
>>> any(flag == 0 for (_, _, flag) in items)
True
发布于 2012-05-19 22:55:20
如果要检查列表中是否有任何项违反了某个条件,请使用all
if all([x[2] == 0 for x in lista]):
# Will run if all elements in the list has x[2] = 0 (use not to invert if necessary)
要删除所有不匹配的元素,请使用filter
# Will remove all elements where x[2] is 0
listb = filter(lambda x: x[2] != 0, listb)
发布于 2012-05-19 22:54:08
你可以像这样使用itertools的提取,一旦你的语句不符合条件,它就会停止。相反方法是dropwhile
for x in itertools.takewhile(lambda x: x[2] == 0, list)
print x
https://stackoverflow.com/questions/10666163
复制相似问题