mangledpotat0
mangledpotat0

Reputation: 3

Numpy: how do I apply masks vectorwise?

I have a numpy array that is a list of vectors, like

arr1 = [ [ 1, 2 ], [ 2, 2 ], [ 5, 3 ], [ 9, -1 ], [ 6, 3 ], ... ]

corresponding to x,y value pairs. I would like to set up a mask using criteria for both the x and y components, for example 0 < x < 4 and 0 < y < 7, in such a way that the mask for the above looks like:

[ [ True, True ], [ True, True ], [ False, False ], [ False, False ], [ False, False ], ... ]

In other words, for each vector in the array, I want the mask to have the same truth value for both components, and only return True if the conditions for x and y are both satisfied. I tried something like:

masked = numpy.ma.array(arr1, mask= [0<arr1[:,0]<4 & 0<arr1[:,1]<7, 0<arr1[:,0]<4 & 0<arr1[:,1]<7])

But it tells me "The truth value of an array with more than one element is ambiguous." Is there a way to do this concisely without using loops or if elses?

Upvotes: 0

Views: 110

Answers (1)

yatu
yatu

Reputation: 88275

Using the input array:

print(arr1)
array([[ 1,  2],
       [ 2,  2],
       [ 5,  3],
       [ 9, -1],
       [ 6,  3]])

You can check for the conditions on each of the columns individually (do note that chained comparisons don't work in NumPy). Then take the bitwise AND of both conditions and broadcast to the shape of the array:

x = arr1[:,0] 
y = arr1[:,1] 

c1 = (x>0)&(x<4)
c2 = (y>0)&(y<7)

np.broadcast_to((c1&c2)[:,None], arr1.shape)
array([[ True,  True],
       [ True,  True],
       [False, False],
       [False, False],
       [False, False]])

Upvotes: 1

Related Questions