用于有条件地减去现有值的 Numpy 布尔索引掩码
Numpy boolean index mask for conditional subtraction of existing values
我有一个范围为 (0, 180) 的 numpy 数字数组。对于这些值中的每一个,如果值 x 大于 90,我想将其替换为 180 - x .
例如5 -> 5, 50 -> 50, 100 -> 80, 175 -> 5.
因为 numpy 的强大之处在于它能够同时对整个数组进行操作,例如a = a + 1 将 a 中的所有项目递增 1,我使用布尔掩码尝试了以下操作:
>>> import numpy as np
>>> a = np.random.randint(180, size=(20))
>>> a
array([150, 136, 28, 77, 7, 165, 114, 71, 150, 86, 129, 156, 33,
34, 91, 87, 105, 9, 5, 108])
>>> a[a > 90] = 180 - a
Traceback (most recent call last):
File "<stdin>", line 1, in <module>
ValueError: NumPy boolean array indexing assignment cannot assign 20 input values to the 10 output values where the mask is true
>>>
这失败了,因为掩码数组和原始数组的长度不匹配。
我该怎么做(无需手动遍历数组)?
一种方法是使用 np.where
:
>>> a
array([172, 47, 58, 47, 162, 130, 16, 173, 125, 40, 25, 32, 123,
142, 89, 29, 120, 2, 97, 116])
>>> np.where(a>90, 180-a, a)
array([ 8, 47, 58, 47, 18, 50, 16, 7, 55, 40, 25, 32, 57, 38, 89, 29, 60,
2, 83, 64])
注意,这个returns是一个新的数组,而不是修改现有的数组。如果需要,您可以将它重新分配给 a
,但更改不会被引用原始数组的任何其他变量 "seen"。
你也可以做你所做的,如果你select赋值两边的适当元素:
>>> a[a>90] = 180 - a[a>90]
>>> a
array([ 8, 47, 58, 47, 18, 50, 16, 7, 55, 40, 25, 32, 57, 38, 89, 29, 60,
2, 83, 64])
我有一个范围为 (0, 180) 的 numpy 数字数组。对于这些值中的每一个,如果值 x 大于 90,我想将其替换为 180 - x .
例如5 -> 5, 50 -> 50, 100 -> 80, 175 -> 5.
因为 numpy 的强大之处在于它能够同时对整个数组进行操作,例如a = a + 1 将 a 中的所有项目递增 1,我使用布尔掩码尝试了以下操作:
>>> import numpy as np
>>> a = np.random.randint(180, size=(20))
>>> a
array([150, 136, 28, 77, 7, 165, 114, 71, 150, 86, 129, 156, 33,
34, 91, 87, 105, 9, 5, 108])
>>> a[a > 90] = 180 - a
Traceback (most recent call last):
File "<stdin>", line 1, in <module>
ValueError: NumPy boolean array indexing assignment cannot assign 20 input values to the 10 output values where the mask is true
>>>
这失败了,因为掩码数组和原始数组的长度不匹配。 我该怎么做(无需手动遍历数组)?
一种方法是使用 np.where
:
>>> a
array([172, 47, 58, 47, 162, 130, 16, 173, 125, 40, 25, 32, 123,
142, 89, 29, 120, 2, 97, 116])
>>> np.where(a>90, 180-a, a)
array([ 8, 47, 58, 47, 18, 50, 16, 7, 55, 40, 25, 32, 57, 38, 89, 29, 60,
2, 83, 64])
注意,这个returns是一个新的数组,而不是修改现有的数组。如果需要,您可以将它重新分配给 a
,但更改不会被引用原始数组的任何其他变量 "seen"。
你也可以做你所做的,如果你select赋值两边的适当元素:
>>> a[a>90] = 180 - a[a>90]
>>> a
array([ 8, 47, 58, 47, 18, 50, 16, 7, 55, 40, 25, 32, 57, 38, 89, 29, 60,
2, 83, 64])