让x
是 np.array
形状(n, m)
.
让y
是 np.array
形状(n, k)
.
计算张量的正确方法是什么 z
形状(n, m, k)
这样
for all i in [0, n - 1]
z[i] = np.dot(x[i][:, np.newaxis], y[i][np.newaxis, :])
?
换句话说,每对行(x_i, y_i)
给出一个形状为 (m, k)
的矩阵.
我查看了np.tensordot
但经过多次试验,我找不到其 axes
的正确值争论。我不确定它是否适合这项工作。
最佳答案
您可以像这样使用np.einsum()
:
z = np.einsum('ij,ik->ijk', x, y)
根据快速测试,这也比基于 np.matmul()
的方法更快(除了非常小的输入):
import numpy as np
x = np.random.randint(1, 100, (2, 3))
y = np.random.randint(1, 100, (2, 4))
%timeit np.einsum('ij,ik->ijk', x, y)
# 100000 loops, best of 3: 3.14 µs per loop
%timeit np.matmul(x[:, :, None], y[:, None, :])
# 100000 loops, best of 3: 2,07 µs per loop
x = np.random.randint(1, 100, (20, 30))
y = np.random.randint(1, 100, (20, 40))
%timeit np.einsum('ij,ik->ijk', x, y)
# 10000 loops, best of 3: 32.1 µs per loop
%timeit np.matmul(x[:, :, None], y[:, None, :])
# 10000 loops, best of 3: 76.8 µs per loop
x = np.random.randint(1, 100, (200, 300))
y = np.random.randint(1, 100, (200, 400))
%timeit np.einsum('ij,ik->ijk', x, y)
# 10 loops, best of 3: 48.7 ms per loop
%timeit np.matmul(x[:, :, None], y[:, None, :])
# 10 loops, best of 3: 68.2 ms per loop
将np.dot()
应用于可广播 View ,如下所示:
np.dot(x[:, :, None], y[:, None, :])
不起作用(它甚至不会达到正确的形状)。
(已编辑)
关于numpy (n, m) 和 (n, k) 到 (n, m, k),我们在Stack Overflow上找到一个类似的问题: https://stackoverflow.com/questions/59896902/