numpy.einsum('ij,ji',a,b)性能问题

时间:2019-11-13 20:15:07

标签: python numpy numpy-einsum

有人可以解释一下,为什么numpy.einsum('ij,ji',A,B)比numpy.einsum('ij,ij',A,B)慢得多,如下所示?

In [1]: import numpy as np
In [2]: a = np.random.rand(1000,1000)                                                                                                                                
In [3]: b = np.random.rand(1000,1000)                                                                                                                                
In [4]: timeit np.einsum('ij,ij', a, b)                                                                                                                               
532 µs ± 5.36 µs per loop (mean ± std. dev. of 7 runs, 1000 loops each)
In [5]: timeit np.einsum('ij,ji', a, b)                                                                                                                               
1.28 ms ± 20.9 µs per loop (mean ± std. dev. of 7 runs, 1000 loops each)

关于, 马雷克

1 个答案:

答案 0 :(得分:2)

第一嫌疑犯:https://en.wikipedia.org/wiki/Locality_of_reference#Spatial_and_temporal_locality_usage

在第一种情况下,ab的内存都以连续的顺序模式进行访问。

在第二种情况下,b的内存在内部循环中以1000个元素(8000字节)的步幅进行访问。

大多数现代x86处理器都具有32KiB L1高速缓存和64字节高速缓存行,这意味着总共有512个高速缓存行。因此,整个L1缓存在外循环迭代之间被驱逐了两次。

请注意,如果您运行

timeit np.einsum('ij,ji', a, b.T)

您应该获得与第一个示例大致相同的时间。

类似地

timeit np.einsum('ij,ij', a, b.T)

应该给您第二个示例相同的时间。