Warning: file_get_contents(/data/phpspider/zhask/data//catemap/2/python/283.json): failed to open stream: No such file or directory in /data/phpspider/zhask/libs/function.php on line 167

Warning: Invalid argument supplied for foreach() in /data/phpspider/zhask/libs/tag.function.php on line 1116

Notice: Undefined index: in /data/phpspider/zhask/libs/function.php on line 180

Warning: array_chunk() expects parameter 1 to be array, null given in /data/phpspider/zhask/libs/function.php on line 181
Python NumPy ndarray广播-形状(X,)与(X,1)以(X,Y)操作_Python_Numpy_Multidimensional Array_Array Broadcasting - Fatal编程技术网

Python NumPy ndarray广播-形状(X,)与(X,1)以(X,Y)操作

Python NumPy ndarray广播-形状(X,)与(X,1)以(X,Y)操作,python,numpy,multidimensional-array,array-broadcasting,Python,Numpy,Multidimensional Array,Array Broadcasting,我有一个NumPyndarray,它的形状是(321024),包含32个信号测量值,我想将它们组合成一个1024个元素的长数组,32个元素中的每一个都有不同的权重。我使用的是numpy.average,但我的权重很复杂,average根据结果的总和对权重进行归一化 通过查看平均值的代码,我意识到我可以通过将权重乘以信号数组,然后在第一个轴上求和来完成同样的事情。但是,当我尝试将(32,)权重数组乘以(32,1024)信号数组时,由于(32,)不能广播到(32,1024),我得到了一个维度不匹配。

我有一个NumPy
ndarray
,它的形状是(321024),包含32个信号测量值,我想将它们组合成一个1024个元素的长数组,32个元素中的每一个都有不同的权重。我使用的是
numpy.average
,但我的权重很复杂,
average
根据结果的总和对权重进行归一化

通过查看平均值的代码,我意识到我可以通过将权重乘以信号数组,然后在第一个轴上求和来完成同样的事情。但是,当我尝试将(32,)权重数组乘以(32,1024)信号数组时,由于(32,)不能广播到(32,1024),我得到了一个维度不匹配。如果我将权重数组重塑为(32,1),那么一切都会按预期工作,但是这会导致相当难看的代码:

avg = (weights.reshape((32, 1)) * data).sum(axis=0)

有人能解释为什么NumPy不允许我的(32,)数组向(32,1024)广播和/或建议一种替代的、更简洁的加权平均方法吗?

(X,)
(X,Y)
形状数组之间对齐的通用设置

关于为什么
(32,)
不能广播到
(321024)
的问题,这是因为形状没有正确对齐。要将其放入示意图中,我们有:

weights :         32
data    :  32 x 1024 
我们需要将唯一的轴对齐,即
权重的第一个轴
数据的第一个轴对齐。因此,正如您所发现的,一种方法是将
重塑为
2D
,这样我们将以一个单体维度作为第二个轴。这可以通过引入一个新轴来实现,该轴具有:
权重[:,np.newaxis]
权重[:,无]
或简单的重塑:
权重。重塑(-1,1)
。因此,回到示意图,使用修改后的版本,我们将:

weights[:,None] :  32 x    1
data            :  32 x 1024
现在,形状已经对齐,我们可以在这两者之间执行任何通用的元素操作,结果示意图如下所示-

weights[:,None] :  32 x    1
data            :  32 x 1024
result          :  32 x 1024
weights.dot(data)
这将广播
权重
,并使用
数据
执行相关的元素操作,从而产生
结果

解决我们的具体案例和备选方案

根据上一节中的讨论,要解决元素相乘的情况,将是
权重[:,无]*数据
,然后沿
轴=0
求和,即-

(weights[:,None]*data).sum(axis=0)
让我们来寻找合适的替代方案

一种简洁且可能直观的方法是-

另一种方法是使用矩阵乘法,因为我们失去了
权重的第一个轴与
数据的第一个轴,如下所示-

weights[:,None] :  32 x    1
data            :  32 x 1024
result          :  32 x 1024
weights.dot(data)

numpy可以将(32,)扩展到
(1,32)
(1024,32)
;但是您必须授予它将
(32,)
扩展到
(32,1)
的权限。这可以避免在其他情况下出现歧义,例如,将a(32,)乘以a(1024,)。在我最近的回答中有更多关于这一点的内容,清晰而彻底的回答,谢谢。我不知道
np.einsum
——虽然这是一种公认的简洁方法,但我认为对于不熟悉语法的人来说,这并不明显。
np.dot
样式更接近于“合理”且紧凑的东西。