A colleague just showed me this indexing behavior and I was at a loss to explain what was going on. Can anybody else chime in and help me understand this indexing behavior? >>> import numpy as np >>> np.__version__ '1.7.1' >>> A = np.ones((2,3,5)) >>> mask = np.array([True]*4 + [False], dtype=bool) >>> A.shape (2, 3, 5) >>> A[:,:,mask].shape (2, 3, 4) >>> A[:,1,mask].shape (2, 4) >>> A[1,:,mask].shape (4, 3) # Why is this not (3, 4)? >>> A[1][:,mask].shape (3, 4) Thanks! Brad
On Tue, 2013-07-02 at 20:44 -0700, Bradley M. Froehle wrote:
A colleague just showed me this indexing behavior and I was at a loss to explain what was going on. Can anybody else chime in and help me understand this indexing behavior?
>>> import numpy as np >>> np.__version__ '1.7.1' >>> A = np.ones((2,3,5)) >>> mask = np.array([True]*4 + [False], dtype=bool) >>> A.shape (2, 3, 5) >>> A[:,:,mask].shape (2, 3, 4) >>> A[:,1,mask].shape (2, 4) >>> A[1,:,mask].shape (4, 3) # Why is this not (3, 4)? >>> A[1][:,mask].shape (3, 4)
Numpy has slicing and fancy indexing. But scalars are both. They are fancy indexes, but they do not trigger fancy indexing (you could also add the special case of a scalar result to this, but it doesn't matter for this)! Implementation wise mixed fancy indexing/slicing is a multi step process: 1. Evaluate the slices. (no surprises here) 2. Evaluate the fancy indexing moving the new axes to the *front*. Here this means A[1,:,mask] -> A.transpose(2,0,1) then combining all fancy indexes so that A.shape goes from (2, 3, 5) via transpose (5,2,3) to (4,3), since the combination of 1 and mask gives a 1-d result with 4 entries. 3. If and only if all fancy indexes were consecutive, i.e. A[:,1,mask], A[mask,[[3]],:], numpy can basically guess where it would make sense to put the fancy axes. So it transposes it back. This is what makes a single fancy index behave like a slice. Now in your example A[1,:,mask] is *not* consecutive (remember scalars are fancy in this regard), so the fancy axis goes to the front instead of going to where "mask" was. In short, the resulting axes from the fancy indices is at the front if the fancy indices are not consecutive. And since scalars are considered fancy in this regard they are not consecutive in your example. - Sebastian
Thanks! Brad _______________________________________________ NumPy-Discussion mailing list NumPy-Discussion@scipy.org http://mail.scipy.org/mailman/listinfo/numpy-discussion
participants (2)
-
Bradley M. Froehle -
Sebastian Berg