I need to mask an array a
by a condition fulfilled by another array b
.
For example values in a
should only be preserved if the values in the same position of b
equal 0, otherwise return as None
. For example:
a = np.array([2, 2, 4, 0, 4, 3, 3, 3, 1, 2])
is masked by
b = np.array([0, 0, 0, 1, 0, 3, 0, 5, 0, 0])
to return
c: [2, 2, 4, None, 4, None, 3, None, 1, 2]
I have tried
to_change = np.ma.masked_where(travel_time!=0, new_subareas)
but this returns:
masked_array(data=[2, 2, 4, --, 4, --, 3, --, 1, 2],
mask=[False, False, False, True, False, True,
False, True, False, False],
fill_value=999999)
But I can't find anything that will just return something like the example given for c
.
I need something done entirely in numpy
and without for-loops or if statements, for speed as this will be for very large arrays.
What am I missing?
If you need an in-place solution, you can convert to a
to float
and then use np.where
.
Float conversion is required here as np.nan
is a float
.
a = np.array([2, 2, 4, 0, 4, 3, 3, 3, 1, 2])
b = np.array([0, 0, 0, 1, 0, 3, 0, 5, 0, 0])
a = a.astype(float)
a[np.where(b!=0)] = np.nan
# array([ 2., 2., 4., nan, 4., nan, 3., nan, 1., 2.])
masked_array
s have a little more overhead, in that operations on these implicitly ignore masked values (and work on everything else instead).
If you are not looking for that kind of functionality, you can just use np.where
, but you risk converting your array to an object
.
np.where(b == 0, a, None)
array([2, 2, 4, None, 4, None, 3, None, 1, 2], dtype=object)
I'd recommend substitution with NaN
instead?
np.where(b == 0, a, np.nan)
array([ 2., 2., 4., nan, 4., nan, 3., nan, 1., 2.])
Preserves the numeric type.
If you love us? You can donate to us via Paypal or buy me a coffee so we can maintain and grow! Thank you!
Donate Us With