我想从一个大约有一百万个条目的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.
我能用其他的方式完成这件事吗?
我假设你的意思是 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
>>> 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])
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])
a < -100 或 a > -100
的反命题是a >= -100 并且 a <= 100
。请参考德摩根定理。 - falsetru