Reputation: 307
lets say i have one array
a = numpy.arange(8*6*3).reshape((8, 6, 3))
#and another:
l = numpy.array([[0,0],[0,1],[1,1]]) #an array of indexes to array "a"
#and yet another:
b = numpy.array([[0,0,5],[0,1,0],[1,1,3]])
where "l" and "b" are of equal length, and i want to say
a[l] = b
such that a[0][0] becomes [0,0,5], a[0][1] becomes [0,1,0] etc.
it seems to work fine when ive got one-dimensional arrays, but it gives me the error
ValueError: array is not broadcastable to correct shape
when i try it with a 3-dimensional array.
Upvotes: 4
Views: 3223
Reputation: 879321
import numpy as np
a = np.arange(8*6*3).reshape((8, 6, 3))
l = np.array([[0,0],[0,1],[1,1]]) #an array of indexes to array "a"
b = np.array([[0,0,5],[0,1,0],[1,1,3]])
a[tuple(l.T)] = b
print(a[0,0])
# [0 0 5]
print(a[0,1])
# [0 1 0]
print(a[1,1])
# [1 1 3]
When you are supplying arrays in all index slots, what you get back has the same shape as the arrays you put in; so if you supply one-dimensional lists, like
A[[1,2,3],[1,4,5],[7,6,2]]
what you get is
[A[1,1,7], A[2,4,6], A[3,5,2]]
When you compare that with your example, you see that
a[l] = b
tells NumPy to set
a[0,0,1] = [0,0,5]
a[0,1,1] = [0,1,0]
and leaves the third element of b
unassigned. This is why you get the error
ValueError: array is not broadcastable to correct shape
The solution is to transpose the array l
into the correct shape:
In [50]: tuple(l.T)
Out[50]: (array([0, 0, 1]), array([0, 1, 1]))
(You could also use zip(*l)
, but tuple(l.T)
is a bit quicker.)
Upvotes: 3
Reputation: 71
Or with your same arrays you can use
for i in range(len(l)):
a[l[i][0]][l[i][1]]=b[i]
Upvotes: 0