Mattijn
Mattijn

Reputation: 13930

NumPy array indexing a 2D matrix

I've a little issue while working on same big data. But for now, let's assume I've got an NumPy array filled with zeros

>>> x = np.zeros((3,3))
>>> x
array([[ 0.,  0.,  0.],
       [ 0.,  0.,  0.],
       [ 0.,  0.,  0.]])

Now I want to change some of these zeros with specific values. I've given the index of the cells I want to change.

>>> y = np.array([[0,0],[1,1],[2,2]])
>>> y 
array([[0, 0],
       [1, 1],
       [2, 2]])

And I've got an array with the desired (for now random) numbers, as follow

>>> z = np.array(np.random.rand(3))
>>> z
array([ 0.04988558,  0.87512891,  0.4288157 ])

So now I thought I can do the following:

>>> x[y] = z

But than it's filling the whole array like this

>>> x
array([[ 0.04988558,  0.87512891,  0.4288157 ],
       [ 0.04988558,  0.87512891,  0.4288157 ],
       [ 0.04988558,  0.87512891,  0.4288157 ]])

But I was hoping to get

>>> x
array([[ 0.04988558,           0,          0 ],
       [          0,  0.87512891,          0 ],
       [          0,           0,  0.4288157 ]])

EDIT

Now I've used a diagonal index, but what in the case my index is not just diagonal. I was hoping following works:

>>> y = np.array([[0,1],[1,2],[2,0]])
>>> x[y] = z
>>> x
>>> x
array([[          0,  0.04988558,          0 ],
       [          0,           0, 0.87512891 ],
          0.4288157,           0,          0 ]])

But it's filling whole array just like above

Upvotes: 5

Views: 12245

Answers (1)

Nils Werner
Nils Werner

Reputation: 36849

Array indexing works a bit differently on multidimensional arrays

If you have a vector, you can access the first three elements by using

x[np.array([0,1,2])]

but when you're using this on a matrix, it will return the first few rows. Upon first sight, using

x[np.array([0,0],[1,1],[2,2]])]

sounds reasonable. However, NumPy array indexing works differently: It still treats all those indices in a 1D fashion, but returns the values from the vector in the same shape as your index vector.

To properly access 2D matrices you have to split both components into two separate arrays:

x[np.array([0,1,2]), np.array([0,1,2])]

This will fetch all elements on the main diagonal of your matrix. Assignments using this method is possible, too:

x[np.array([0,1,2]), np.array([0,1,2])] = 1

So to access the elements you've mentioned in your edit, you have to do the following:

x[np.array([0,1,2]), np.array([1,2,0])]

Upvotes: 9

Related Questions