Python 多维Numpy点积比for循环慢

Python 多维Numpy点积比for循环慢,python,arrays,numpy,matrix,Python,Arrays,Numpy,Matrix,对于小矩阵乘法,使用mkl优化的numpy似乎相当快,而对于高维张量收缩,则相当慢。例如,使用einsum之类的函数要比在高维复张量的二维子矩阵中循环慢得多: complexarray = np.random.rand(2867, 100, 40) + 1j*np.random.rand(2867, 100, 40) complexarray_cc = complexarray.conj() %timeit np.einsum('ijk, ijm -> jkm', complexarr

对于小矩阵乘法,使用mkl优化的numpy似乎相当快,而对于高维张量收缩,则相当慢。例如,使用einsum之类的函数要比在高维复张量的二维子矩阵中循环慢得多:

complexarray = np.random.rand(2867, 100, 40) + 1j*np.random.rand(2867, 100, 40)
complexarray_cc = complexarray.conj()


%timeit np.einsum('ijk, ijm -> jkm', complexarray_cc, complexarray)
1圈,最佳3圈:每圈2.45秒

%%timeit 
tmp_product = np.zeros((100,40,40), dtype=complex)
for l in range(100):
    tmp_product[l,:,:] = np.dot((complexarray_cc[:,l,:].T), complexarray[:,l,:])
10个回路,最好为3:120 ms/回路

%%timeit 
tmp_product = np.zeros((100,40,40), dtype=complex)
for l in range(100):
    tmp_product[l,:,:] = np.dot((complexarray_cc[:,l,:].T), complexarray[:,l,:])
看着

这描述了一个类似的问题,似乎数组太大,无法放入内存,因此使用了一些缓慢的矩阵乘法例程。这里会是这样吗

天真地,我的方法是用矢量化的numpy/数组操作替换代码中的任何for循环。随着阵列变得越来越大,这似乎不是任意可伸缩的


是否没有其他选项来增加np.dot和类似操作的操作?或者换言之:与在超大阵列上使用numpy函数相比,建议在较小的子阵列上循环到哪一点?

与在超大阵列上使用numpy函数相比,建议在较小的子阵列上循环到哪一点?
-我认为这在很大程度上取决于输入数组的形状。例如,如果第二个轴的长度与第一个轴的长度相比是一个巨大的数字,我怀疑loopy dot product是否仍然是赢家。
einsum
没有使用我所知道的任何
mkl
优化。它使用
nditer
(2867100,40,40)
空间上迭代。@hpaulj是正确的。einsum代码在许多方面都非常幼稚,而
np.dot
将调用DGEMM(线程化、矢量化等)。通常,使用numpy可以避免python循环,在这里,它们是最理想的方法,除非循环索引的大小与
dot
大小之间的比率发生显著变化。有时,我使用einsum时遇到了一个非常快的最佳点,甚至比np.dot还要快,有时它会像上面的例子一样慢。对于大于3维的大型阵列,除了使用for循环外,还有其他方法可以替代numpy吗?