简体   繁体   English

基于过滤器从python列表中删除元素

[英]Remove elements from python list based on filter

I have 3 lists in Python. 我在Python中有3个列表。

list_a = [10., 20., 30., 12.]
list_b = [30., 20., 60., 12.]
list_c = [10., 80., 90., 12.]

I want to drop those elements in list_b and list_c where values in list_a are <= 15 . 我想删除那些元素在list_blist_c其中值list_a<= 15 Therefore results become: 因此结果变为:

list_b = [20., 60.]
list_c = [80., 90.]

Is there a way to do this without for loops? 有没有办法在没有循环的情况下做到这一点? (list comprehensions are ok) (列表理解还可以)

If you are using numpy as you said you are, in comments, you can simply create a boolean index from a and mask elements in b and c : 如果您正在使用numpy的,你说你在评论,你可以简单地创建从布尔指数a中和掩码元素bc

import numpy as np

list_a = np.array([10., 20., 30., 12.])
list_b = np.array([30., 20., 60., 12.])
list_c = np.array([10., 80., 90., 12.])

list_b = list_b[list_a>15]
list_c = list_c[list_a>15]

print list_a
print list_b
print list_c

Output: 输出:

[ 10.  20.  30.  12.]
[ 20.  60.]
[ 80.  90.]

You can convert the lists_b and list_c to Python list type by .tolist() method. 您可以通过.tolist()方法将lists_blist_c转换为Python list type

You can use the little known itertools.compress class to do this. 您可以使用鲜为人知的itertools.compress类来执行此操作。 See Filter list using Boolean index arrays 请参阅使用布尔索引数组筛选列表

>>> import itertools
>>> list_a = [10., 20., 30., 12.]
>>> list_b = [30., 20., 60., 12.]
>>> list_c = [10., 80., 90., 12.]
>>> bool_list = [item > 15 for item in list_a]
>>> bool_list
[False, True, True, False]
>>> list_b = list(itertools.compress(list_b, bool_list))
>>> list_b
[20.0, 60.0]
>>> list_c = list(itertools.compress(list_c, bool_list))
>>> list_c
[80.0, 90.0]

You may write a one-liner to filter the list via using zip() as: 您可以使用zip()编写一个单行来过滤列表:

list_b, list_c = zip(*[(b, c) for a, b, c in zip(list_a, list_b, list_c) if a>15])

The final values hold by list_b and list_c will be: list_blist_c持有的最终值将是:

>>> list_b
(20.0, 60.0)
>>> list_c
(80.0, 90.0)

Can you use list comprehensions? 你能使用列表推导吗?

You could do it like this: 你可以这样做:

list_a = [10., 20., 30., 12.]
list_b = [30., 20., 60., 12.]
list_c = [10., 80., 90., 12.]
list_b = [ el for (i, el) in enumerate(list_b) if (list_a[i] > 15) ]
list_c = [ el for (i, el) in enumerate(list_c) if (list_a[i] > 15) ]

Snipper was written here, I haven't tested it, but you see the general idea. Snipper写在这里,我还没有测试过,但你看到了一般的想法。

I assumed that all lists are the same length. 我假设所有列表都是相同的长度。 If list_a is shorter and you want to drop elements that are on the missing positions, you can do it like this: 如果list_a较短并且您想要删除缺失位置上的元素,则可以这样做:

list_b = [ el for (i, el) in enumerate(list_b) if (i<len(list_a) and list_a[i] > 15) ]

and if you want to keep them, just reverse the sign and boolean operator: 如果你想保留它们,只需反转符号和布尔运算符:

list_b = [ el for (i, el) in enumerate(list_b) if (i>=len(list_a) or list_a[i] > 15) ]

You can zip() like below: 你可以像下面的zip()

>>> list_a = [10., 20., 30., 12.]
>>> list_b = [30., 20., 60., 12.]
>>> list_c = [10., 80., 90., 12.]
>>>
>>> [j for i,j in zip(list_a, list_b) if i >= 15]
[20.0, 60.0]
>>>
>>> [j for i,j in zip(list_a, list_c) if i >= 15]
[80.0, 90.0]
list_a = [10., 20., 30., 12.]
list_b = [30., 20., 60., 12.]
list_c = [10., 80., 90., 12.]
drop = [i for i,v in enumerate(list_a) if v <=15]
b = [v for i,v in enumerate(list_b) if not i in drop]
c = [v for i,v in enumerate(list_c) if not i in drop]

声明:本站的技术帖子网页,遵循CC BY-SA 4.0协议,如果您需要转载,请注明本站网址或者原文地址。任何问题请咨询:yoyou2525@163.com.

 
粤ICP备18138465号  © 2020-2024 STACKOOM.COM