虽然你的问题标题有点不准确,但我认为你遇到的问题主要与 numpy
的broadcasting规则有关。因此,以下操作是无效的(就像你已经发现的那样):
In []: N= 5
In []: A= rand(N, 2)
In []: A.shape
Out[]: (5, 2)
In []: S= rand(N)
In []: S.shape
Out[]: (5,)
In []: A* S
------------------------------------------------------------
Traceback (most recent call last):
File "<ipython console>", line 1, in <module>
ValueError: operands could not be broadcast together with shapes (5,2) (5)
然而,现在使
S
与广播规则(即
A*S
的逐元素乘积)兼容的简单方法是扩展其维度,例如:
In []: A* S[:, None]
Out[]:
array([[ 0.54216549, 0.04964989],
[ 0.41850647, 0.4197221 ],
[ 0.03790031, 0.76744563],
[ 0.29381325, 0.53480765],
[ 0.0646535 , 0.07367852]])
但这实际上只是expand_dims的语法糖,例如:
In []: expand_dims(S, 1).shape
Out[]: (5, 1)
无论如何,我个人更喜欢这种简单而不费力的方法:
In []: S= rand(N, 1)
In []: S.shape
Out[]: (5, 1)
In []: A* S
Out[]:
array([[ 0.40421854, 0.03701712],
[ 0.63891595, 0.64077179],
[ 0.03117081, 0.63117954],
[ 0.24695035, 0.44950641],
[ 0.14191946, 0.16173008]])
因此,使用Python
编程时,显式比隐式更为直观。
reshape
创建的是一个视图,而不是一个副本:>>> s = numpy.arange(5); s.reshape(5, 1)[3,0] = 99; repr(s)
->'array([ 0, 1, 2, 99, 4])'
. 因此,您可以只需执行A * B.reshape(5, 1)
而不更改B
。 - senderle