我在内存中有两个连续的 n×3 块(“长度为 3 的 n 个向量”),我想尽可能快地计算每行之间的点积。据我所知,在 numpy 中,usingeinsum
是最快的变体(einsum("ij,ij->i", a, b)
)。
我已经将它与转置的变体(在内存中也是连续的)进行了比较,即两个 3×n 块。在这里,每个组件 ( x
, y
, z
) 在内存中形成一个大块,而不是 n 个连续的 3 块。我发现这里的计算速度大约是原来的两倍:
我在向量,所以我会对超出这一点的结果感兴趣。
关于为什么转置变体在该尺寸范围内如此之快的任何想法?
重现情节的代码:
import numpy
import perfplot
def setup(n):
a = numpy.random.rand(n, 3)
b = numpy.random.rand(n, 3)
aT = numpy.ascontiguousarray(a.T)
bT = numpy.ascontiguousarray(b.T)
return (a, b), (aT, bT)
perfplot.save(
"rel.png",
setup=setup,
n_range=[2 ** k for k in range(1, 25)],
kernels=[
lambda data: numpy.einsum("ij, ij->i", data[0][0], data[0][1]),
lambda data: numpy.einsum("ij, ij->j", data[1][0], data[1][1]),
],
labels=["einsum", "einsum.T"],
xlabel="len(a), len(b)",
relative_to=1,
flops=lambda n: n,
)