indexing numpy array with logical operator

13,756

Solution 1

This should work

np.where((a1[:,1]>l1) & (a1[:,1]<l2))

or

np.where(np.logical_and(a1[:,1]>l1, a1[:,1]<l2))

Solution 2

Does this do what you want?

import numpy as np
a1 = np.zeros( (500,2) )
a1[:,0]=np.arange(0,500)
a1[:,1]=np.arange(0.5,1000,2)
c=(a1[:,1]>l1)*(a1[:,1]<l2) # boolean array, true if the item at that position is ok according to the criteria stated, false otherwise 
print a1[c] # prints all the points in a1 that correspond to the criteria 

afterwards you can than just select from your new array that you make, the points that you need (assuming your new array has dimensions (500,n)) , by doing

print newarray[c,:]
Share:
13,756
gluuke
Author by

gluuke

Just a computational material scientist ... ;)

Updated on July 12, 2022

Comments

  • gluuke
    gluuke almost 2 years

    I have a 2d numpy array, for instance as:

    import numpy as np
    a1 = np.zeros( (500,2) )
    
    a1[:,0]=np.arange(0,500)
    a1[:,1]=np.arange(0.5,1000,2)
    # could be also read from txt
    

    then I want to select the indexes corresponding to a slice that matches a criteria such as all the value a1[:,1] included in the range (l1,l2):

    l1=20.0; l2=900.0; #as example
    

    I'd like to do in a condensed expression. However, neither:

    np.where(a1[:,1]>l1 and a1[:,1]<l2)
    

    (it gives ValueError and it suggests to use np.all, which it is not clear to me in such a case); neither:

    np.intersect1d(np.where(a1[:,1]>l1),np.where(a1[:,1]<l2))
    

    is working (it gives unhashable type: 'numpy.ndarray')

    My idea is then to use these indexes to map another array of size (500,n).

    Is there any reasonable way to select indexes in such way? Or: is it necessary to use some mask in such case?

  • Eelco Hoogendoorn
    Eelco Hoogendoorn over 10 years
    It would be preferable to use np.logical_and(), rather than the multiplication. Afaik they will give identical results and identical performance under all relevant circumstances, but it makes the structure of the code more explicit.
  • usethedeathstar
    usethedeathstar over 10 years
    @EelcoHoogendoorn not exactly certain what you mean by "more explicit", but to me the multiplication is more readable, though thats maybe due to my maths background, and that for a programmer the "np.logical_and" is more readable?
  • Eelco Hoogendoorn
    Eelco Hoogendoorn over 10 years
    I also have a maths background; from that perspective, the type of the > operator is a bool, so it makes sense to use a logical operator. In most languages or formal systems, multiplication for bools is not even defined as an operator. From a CS perspective; what happens with the multiply is an implicit cast from bool to int. The Zen of Python would have us believe that explicit > implicit. Im a believer, but your mileage may vary ;)