numpy中两个一维向量的点积
我正在使用 numpy
在 python
中计算向量的乘法。我有一个维度为 n x 1 的向量 x,我想计算 x 和它的转置(x的转置就是把它变成一个横向的向量)。这个过程让我遇到了一些问题,因为 x.T
或者 x.transpose()
对于一维向量没有效果(numpy
对竖向和横向的向量处理是一样的)。
那么,我该如何在 numpy
中计算一个 (n x 1) 和 (1 x n) 的向量乘法呢?
使用 numpy.dot(x, x.T) 得到的是一个标量(就是一个数字),而不是我想要的二维矩阵。
5 个回答
0
另一个选择是使用 numpy.matrix
>>> a = np.matrix([1,2,3])
>>> a
matrix([[1, 2, 3]])
>>> a.T * a
matrix([[1, 2, 3],
[2, 4, 6],
[3, 6, 9]])
通常来说,大家更喜欢用 numpy.arrays
。不过,使用 numpy.matrices
在处理长表达式时可能会更容易理解。
1
另一种选择是用二维来定义行向量或列向量,比如:
a = np.array([1, 2, 3], ndmin=2)
np.dot(a.T, a)
array([[1, 2, 3],
[2, 4, 6],
[3, 6, 9]])
1
如果你想计算内积,可以使用 numpy.dot(x,x)
;如果想计算外积,可以用 numpy.outer(x,x)
。
6
虽然 np.outer
是最简单的方法来实现这个功能,但我想提一下你可以如何处理形状为 (N,)
的数组来做到这一点:
In [17]: a = np.arange(4)
In [18]: np.dot(a[:,None], a[None,:])
Out[18]:
array([[0, 0, 0, 0],
[0, 1, 2, 3],
[0, 2, 4, 6],
[0, 3, 6, 9]])
In [19]: np.outer(a,a)
Out[19]:
array([[0, 0, 0, 0],
[0, 1, 2, 3],
[0, 2, 4, 6],
[0, 3, 6, 9]])
在这里,你可以把 None
替换成 np.newaxis
。
还有一种更特别的方法是使用 np.einsum:
In [20]: np.einsum('i,j', a, a)
Out[20]:
array([[0, 0, 0, 0],
[0, 1, 2, 3],
[0, 2, 4, 6],
[0, 3, 6, 9]])
为了好玩,这里有一些时间测试,结果可能会根据你的硬件和numpy的版本/编译情况有所不同:
小一点的向量
In [36]: a = np.arange(5, dtype=np.float64)
In [37]: %timeit np.outer(a,a)
100000 loops, best of 3: 17.7 µs per loop
In [38]: %timeit np.dot(a[:,None],a[None,:])
100000 loops, best of 3: 11 µs per loop
In [39]: %timeit np.einsum('i,j', a, a)
1 loops, best of 3: 11.9 µs per loop
In [40]: %timeit a[:, None] * a
100000 loops, best of 3: 9.68 µs per loop
还有一些稍微大一点的
In [42]: a = np.arange(500, dtype=np.float64)
In [43]: %timeit np.outer(a,a)
1000 loops, best of 3: 605 µs per loop
In [44]: %timeit np.dot(a[:,None],a[None,:])
1000 loops, best of 3: 1.29 ms per loop
In [45]: %timeit np.einsum('i,j', a, a)
1000 loops, best of 3: 359 µs per loop
In [46]: %timeit a[:, None] * a
1000 loops, best of 3: 597 µs per loop
16
你实际上是在计算一个叫做“外积”的东西。
你可以使用 np.outer
这个函数来实现。
In [15]: a=[1,2,3]
In [16]: np.outer(a,a)
Out[16]:
array([[1, 2, 3],
[2, 4, 6],
[3, 6, 9]])