Python:数组的numpy数组的外积的所有排列的总和

Python:数组的numpy数组的外积的所有排列的总和,python,numpy,array-broadcasting,numpy-ndarray,numpy-einsum,Python,Numpy,Array Broadcasting,Numpy Ndarray,Numpy Einsum,我有一个数组Ai的numpy数组,我希望每个外积(np.outer(Ai[I],Ai[j])用一个缩放倍增器求和以产生H。我可以单步进行,然后用缩放因子矩阵对它们进行拉伸。我认为事情可以大大简化,但还没有找到一个通用/有效的方法来为ND实现这一点。如何更容易地生产Arr2D和H?注意:Arr2D可以是64个2D阵列,而不是8x8个2D阵列 Ai = np.random.random((8,101)) Arr2D = np.zeros((Ai.shape[0], Ai.shape[0], Ai.s

我有一个数组Ai的numpy数组,我希望每个外积(np.outer(Ai[I],Ai[j])用一个缩放倍增器求和以产生H。我可以单步进行,然后用缩放因子矩阵对它们进行拉伸。我认为事情可以大大简化,但还没有找到一个通用/有效的方法来为ND实现这一点。如何更容易地生产Arr2D和H?注意:Arr2D可以是64个2D阵列,而不是8x8个2D阵列

Ai = np.random.random((8,101))
Arr2D = np.zeros((Ai.shape[0], Ai.shape[0], Ai.shape[1], Ai.shape[1]))
Arr2D[:,:,:,:] = np.asarray([ np.outer(Ai[i], Ai[j]) for i in range(Ai.shape[0]) 
    for j in range(Ai.shape[0]) ]).reshape(Ai.shape[0],Ai.shape[0],Ai[0].size,Ai[0].size)
arr = np.random.random( (Ai.shape[0] * Ai.shape[0]) )
arr2D = arr.reshape(Ai.shape[0], Ai.shape[0])
H = np.tensordot(Arr2D, arr2D, axes=([0,1],[0,1]))

利用
einsum的良好设置

np.einsum('ij,kl,ik->jl',Ai,Ai,arr2D,optimize=True)
时间安排-

In [71]: # Setup inputs
    ...: Ai = np.random.random((8,101))
    ...: arr = np.random.random( (Ai.shape[0] * Ai.shape[0]) )
    ...: arr2D = arr.reshape(Ai.shape[0], Ai.shape[0])

In [74]: %%timeit # Original soln
    ...: Arr2D = np.zeros((Ai.shape[0], Ai.shape[0], Ai.shape[1], Ai.shape[1]))
    ...: Arr2D[:,:,:,:] = np.asarray([ np.outer(Ai[i], Ai[j]) for i in range(Ai.shape[0]) 
    ...:     for j in range(Ai.shape[0]) ]).reshape(Ai.shape[0],Ai.shape[0],Ai[0].size,Ai[0].size)
    ...: H = np.tensordot(Arr2D, arr2D, axes=([0,1],[0,1]))
100 loops, best of 3: 4.5 ms per loop

In [75]: %timeit np.einsum('ij,kl,ik->jl',Ai,Ai,arr2D,optimize=True)
10000 loops, best of 3: 146 µs per loop
30x+
在那里加速