使用条件检查从numpy数组中删除特定元素

22

我想从一个大约有一百万个条目的numpy数组中删除一些条目。

这段代码可以实现,但会花费很长时间:

a = np.array([1,45,23,23,1234,3432,-1232,-34,233])
for element in a:
    if element<(-100) or element>100:
         some delete command.

我能用其他的方式完成这件事吗?

3个回答

38

我假设你的意思是 a < -100 or a > -100,最简洁的方法是使用逻辑索引。

a = a[(a >= -100) & (a <= 100)]

这并不完全是“删除”条目,而是复制数组中不需要的值,并将其分配给以前分配给旧数组的变量。发生这种情况后,旧数组没有剩余的引用,并且被垃圾收集,这意味着它的内存被释放。

值得注意的是,这种方法不使用恒定的内存,因为我们复制了数组,它会使用与数组大小成线性关系的内存。如果您的数组非常巨大,达到计算机内存的极限,那么这可能是不好的。实际上通过遍历并在数组中“原地”删除每个元素的过程,即使用恒定的内存,将是一种非常不同的操作,因为数组中的元素需要交换并且内存块需要调整大小。我不确定您是否可以对numpy数组执行此操作,但您可以做的一件事是使用numpy掩码数组以避免复制:

import numpy.ma as ma
mx = ma.masked_array(a, mask = ((a < -100) | (a > 100)) )

对掩码数组的所有操作都会像删除元素一样,但我们实际上并没有真正“删除”它们,它们仍然在内存中,只是与数组关联现在有一个要跳过哪些元素的记录,我们永远不需要在内存中制作数组的副本。此外,如果我们想要恢复已删除的值,只需像这样移除掩码:

mx.mask = ma.nomask

我尝试了你的代码,但它保留了不想要的数字(>100或<-100)。我需要删除这些数字。 - Abhinav Kumar
1
a < -100 或 a > -100 的反命题是 a >= -100 并且 a <= 100。请参考德摩根定理 - falsetru

9
您可以使用反转条件 掩码索引
>>> a = np.array([1,45,23,23,1234,3432,-1232,-34,233])

>>> a[~((a < -100) | (a > 100))]
array([  1,  45,  23,  23, -34])

>>> a[(a >= -100) & (a <= 100)]
array([  1,  45,  23,  23, -34])

>>> a[abs(a) <= 100]
array([  1,  45,  23,  23, -34])

这是 OP 想要元素子集的反向。 - qwwqwwq
@qwwqwwq,OP想要删除它们;应该反转条件。 - falsetru

3
In [140]: a = np.array([1,45,23,23,1234,3432,-1232,-34,233])

In [141]: b=a[(-100<=a)&(a<=100)]

In [142]: b
Out[142]: array([  1,  45,  23,  23, -34])

网页内容由stack overflow 提供, 点击上面的
可以查看英文原文,
原文链接