对 numpy 的转置感到困惑

Baffled by numpy's transpose

让我们来看一个非常简单的例子:一个形状为 (2,3,4) 的数组,忽略值。

>>> a.shape
(2, 3, 4)

当我们转置它并打印尺寸时:

>>> a.transpose([1,2,0]).shape
(3, 4, 2)

所以我是说:将轴索引 2 设为第一个,然后将轴索引 0 设为第二,最后将轴索引 1 设为第三。我应该得到 (4,2,3),对吧?

嗯,我想也许我没有完全理解其中的逻辑。所以我阅读了文档,上面写着:

Use transpose(a, argsort(axes)) to invert the transposition of tensors when using the axes keyword argument.

所以我尝试了

>>> c = np.transpose(a, [1,2,0])
>>> c.shape
(3, 4, 2)
>>> np.transpose(a, np.argsort([1,2,0])).shape
(4, 2, 3)

又变成了完全不同的形状!

有人可以解释一下吗?谢谢

np.argsort([1,2,0]) returns 像 [2,0,1]

这样的数组

所以

np.transpose(a, np.argsort([1,2,0])).shape

表现得像

np.transpose(a, [2,0,1]).shape

没有

np.transpose(a, [1,2,0]).shape
In [259]: a = np.zeros((2,3,4))
In [260]: idx = [1,2,0]
In [261]: a.transpose(idx).shape
Out[261]: (3, 4, 2)

这所做的是取 a.shape[1] 维度并将其放在第一位。 a.shape[2] 是第二个,a.shape[0] 第三个:

In [262]: np.array(a.shape)[idx]
Out[262]: array([3, 4, 2])

transpose不加参数就是完全颠倒轴序。它是熟悉的 2d 转置的扩展(行变成列,列变成行):

In [263]: a.transpose().shape
Out[263]: (4, 3, 2)
In [264]: a.transpose(2,1,0).shape
Out[264]: (4, 3, 2)

什么都不做的转置:

In [265]: a.transpose(0,1,2).shape
Out[265]: (2, 3, 4)

您有一个初始轴顺序和最后一个;如果您不经常使用大小为 3 或更大的列表,那么描述交换可能很难想象。

有些人发现使用 swapaxes 更容易,它只改变坐标轴的顺序。 rollaxis 是另一种方式。

我更喜欢使用 transpose,因为它可以做任何其他人可以做的事情;所以我只需要为一个工具开发一个直观的工具。


argsort评论是这样操作的:

In [278]: a.transpose(idx).transpose(np.argsort(idx)).shape
Out[278]: (2, 3, 4)

也就是把它应用到一个转置的结果上,得到原来的顺序。