numpy.array中没有fortran订单

时间:2018-07-30 19:24:52

标签: python numpy

我看不到以下fortran订单:

import numpy as np
In [143]: np.array([[1,2],[3,4]],order='F')
Out[143]: 
array([[1, 2],
       [3, 4]])

但是在以下情况下它起作用:

In [139]: np.reshape(np.arange(9),newshape=(3,3),order='F')
Out[139]: 
array([[0, 3, 6],
       [1, 4, 7],
       [2, 5, 8]])

那么我在第一个地方做错了吗?

2 个答案:

答案 0 :(得分:6)

当调用numpy.array从现有的Python对象创建数组时,它将为您提供具有原始Python对象具有的 shape 形状的对象。所以,

np.array([[1,2],[3,4]], ...)

会一直给你

np.array([[1, 2],
          [3, 4]])

正是您键入的内容,因此不要感到惊讶。 Fortran顺序和C顺序没有描述数据的形状,它们描述了内存布局。当您打印出一个对象时,NumPy不会显示内存布局是什么,只会显示形状。

当您使用"K"顺序将其展平时,您可以看到该数组确实以Fortran顺序存储,这将保留元素的原始顺序:

>>> a = np.array([[1,2],[3,4]], order="F")
>>> a.flatten(order="K")
array([1, 3, 2, 4])

这是真正将Fortran与C指令区分开的地方:内存布局。大多数NumPy函数不会强迫您考虑内存布局,而是透明地处理不同的布局。

听起来像您要换位,就是反转轴顺序。这可以简单地完成:

>>> b = numpy.transpose(a)
>>> b
array([[1, 3],
       [2, 4]])

这不会创建新数组,而是创建同一数组的新视图:

>>> b.base is a
True

如果您希望数据具有1 2 3 4的内存布局,并具有该[[1,3],[2,4]]的Fortran顺序视图,那么执行此操作的有效方法是存储现有的C顺序的数组,然后对其进行转置,从而生成具有所需内容的Fortran顺序数组,并且不需要多余的副本。

>>> a = np.array([[1, 2], [3, 4]]).transpose()
>>> a.flatten(order="K")
array([1, 2, 3, 4])
>>> a
array([[1, 3],
       [2, 4]])

如果使用Fortran顺序存储原始文档,则转置将导致C顺序,因此您不希望这样做(或者您只关心转置,而内存顺序并不重要?)。无论哪种情况,该数组在NumPy中的外观都相同。

>>> a = np.array([[1, 2], [3, 4]], order="F").transpose()
>>> a.flatten(order="K")
array([1, 3, 2, 4])
>>> a
array([[1, 3],
       [2, 4]])

答案 1 :(得分:0)

构造2D数组的两种方法根本不相等。首先,您指定了数组的结构。在第二个步骤中,您形成了一个数组,然后根据自己的喜好进行了重塑。

>>> np.reshape([1,2,3,4],newshape=(2,2),order='F')
array([[1, 3],
       [2, 4]])

同样,为了进行比较,即使您要求将形状和格式更改为FORTRAN,也将获得指定的结构:

>>> np.reshape([[1,2],[3,4]],newshape=(2,2),order='F')
array([[1, 2],
       [3, 4]])