0

I am a newby in broadcasting with numpy. I define three numpy arrays as follows:

from numpy import *
a=array([10,20]).reshape(2,1)
b=array([100,200,300]).reshape(1,3)
c=arange(1,11).reshape(1,1,10)

a+b is a (2,1) vs (1,3) sum so it is supposed to be broadcastable (2vs1 in dim 1, 1vs3 in dim 2, broadcast rule is fulfiled). Indeed it is:

>>> a+b
array([[110, 210, 310],
       [120, 220, 320]])

a+c is a (2,1) vs (1,1,10) sum so it is supposed to be broadcastable (2vs1 in dim 1, 1vs1 in dim 2 and 1vs10 in dim 3, broadcast rule is fulfiled). Indeed it is:

>>> a+c
array([[[11, 12, 13, 14, 15, 16, 17, 18, 19, 20],
        [21, 22, 23, 24, 25, 26, 27, 28, 29, 30]]])

b+c is a (1,3) vs (1,1,10) sum so it is supposed to be broadcastable (1vs1 in dim 1, 3vs1 in dim 2, 1vs10 in dim 3. But it seems it is not:

>>> b+c
Traceback (most recent call last):
  File "<stdin>", line 1, in <module>
ValueError: shape mismatch: objects cannot be broadcast to a single shape

The explanation is certainely obvious ... but please help me !

2 Answers 2

1
b[:,:,None] + c

returns a (1, 3, 10) array. You have to define the missing axis (the third one).

You can also use

b[:,:,newaxis] + c

since you imported * from numpy, which is generally not a good idea.

import numpy as np is better. This way you will always know where the methods come from (if you import more packages):

import numpy as np
a = np.array([10,20]).reshape(2,1)
b = np.array([100,200,300]).reshape(1,3)
c = np.arange(1,11).reshape(1,1,10)

print a + b
print a + c
print b[:,:,np.newaxis] + c
Sign up to request clarification or add additional context in comments.

1 Comment

Thank you very much ! I know about from numpy import *, I used it for clarity but you are right this should be avoided everywhere.
1

a+c is a (2,1) vs (1,1,10) sum so it is supposed to be broadcastable (2vs1 in dim 1, 1vs1 in dim 2 and 1vs10 in dim 3, broadcast rule is fulfiled). Indeed it is:

>>> a+c array([[[11, 12, 13, 14, 15, 16, 17, 18, 19, 20],
                [21, 22, 23, 24, 25, 26, 27, 28, 29, 30]]])

Not quite, notice that a + c is (1, 2, 10) not (2, 1, 10).

>>> from numpy import array, arange, newaxis
>>> a=array([10,20]).reshape(2,1)
>>> b=array([100,200,300]).reshape(1,3)
>>> c=arange(1,11).reshape(1,1,10)
>>> (a + c).shape
(1, 2, 10).shape

When broadcasting arrays with different dimensions, the one with fewer dimensions get padded with 1s at the beginning, more info here, so b + c is like trying to add a (1, 1, 3) with a (1, 1, 10). @eumiro's suggestion, b[:,:,np.newaxis] + c, is probably the easiest way of reshaping b to be (1,3,1) so you get what you expect.

1 Comment

Thank you Bago, indeed i did not notice that (a+c) was a (1,2,10). And indeed (as suggested by eumiro), to obtain a (2,1,10) I need to write a[:,:,np.newaxis]+c.

Your Answer

By clicking “Post Your Answer”, you agree to our terms of service and acknowledge you have read our privacy policy.

Start asking to get answers

Find the answer to your question by asking.

Ask question

Explore related questions

See similar questions with these tags.