所以我发布了一个问题before,但它太简单了,并且正确地被标记为重复。我现在更详细地发布我的问题,所以希望我的问题可以得到解决。简要说明如下:
我有两个列表:a = [10.0,20.0,25.0,40.0]
和b = [1.0,10.0,15.0,20.0,30.0,100.0]
使用列表推导,我想从b中排除a中指定的元素范围。即:从b中删除10.0和20.0之间以及25.0和40.0之间的所有元素。这是我试过的:
kk = 0
while kk < len(a):
up_lim = a[kk] #upper limit
dwn_lim = a[kk+1] #lower limit
x = [b[y] for y in range(len(b)) if (b[y]<dwn_lim or b[y]>up_lim)] #This line produces correct result if done outside of a while loop. Somehow fails in while loop.
b = list(x) #update the old list with the new&reduced list
kk += 2 #update counter
我期待结果x = [1.0,100.0]
,但我得x = [1.0,10.0,15.0,20.0,30.0,100.0]
事实上,如果我在while循环之外执行它,那么列表理解的关键行就会起作用(当然这是没用的,因为列表&#39; a&#39;可能是任意大小的,这就是为什么我用了一段时间循环)。
所以问题是:while循环如何以及为什么阻止列表理解正确发生?
答案 0 :(得分:4)
使用vanilla python,您可以使用any
/ all
进行推广。我在这里any
。
>>> [x for x in b if not any(i <= x <= j for i, j in zip(a[::2], a[1::2]))]
[1.0, 100.0]
此zip
个zip
每个备用列表项,并逐个检查以确保x
不在其中任何一个中。
如果您对演出感兴趣,请考虑使用熊猫方法。您可以为任务构建Intervalindex
。搜索是对数的,速度非常快。
>>> import pandas as pd
>>> idx = pd.IntervalIndex.from_arrays(a[::2], a[1::2], closed='both')
>>> [x for x, y in zip(b, idx.get_indexer(b)) if y == -1]
[1.0, 100.0]