如何将具有不同第二轴长度的2D Numpy数组展平?

23

我有一个看起来像这样的numpy数组:

myArray = np.array([[1,2],[3]])

但我无法把它压平。

In: myArray.flatten()
Out: array([[1, 2], [3]], dtype=object)

如果我将数组在第二个轴上改为相同的长度,那么我就可以将其压平。

In: myArray2 = np.array([[1,2],[3,4]])
In: myArray2.flatten()
Out: array([1, 2, 3, 4])

我的问题是:

无论数组的维度和元素长度如何,我是否可以像myArray.flatten()这样使用某些东西,并获得输出:array([1,2,3])


3
NumPy不支持不规则数组,而且在使用NumPy处理对象数组(比如这个问题中的列表)时意义不大。例如,2 * myArray会得到array([[1, 2, 1, 2], [3, 3]], dtype=object)。你可能需要重新考虑你的问题或者在代码的早期阶段提出一个问题来了解发生了什么。 - YXD
3个回答

20

myArray是一个一维数组,其中包含对象。使用flatten()ravel()不会改变列表中对象的顺序。您可以使用hstack将数组水平堆叠在序列中:

>>> np.hstack(myArray)
array([1, 2, 3])

注意,这基本等同于在轴1上使用concatenate这在直觉上应该是有意义的):

>>> np.concatenate(myArray, axis=1)
array([1, 2, 3])

如果您没有这个问题,而且可以合并项,使用flatten()ravel()总是更可取的,以获取更好的性能:

In [1]: u = timeit.Timer('np.hstack(np.array([[1,2],[3,4]]))'\
   ....: , setup = 'import numpy as np')
In [2]: print u.timeit()
11.0124390125

In [3]: u = timeit.Timer('np.array([[1,2],[3,4]]).flatten()'\
   ....: , setup = 'import numpy as np')
In [4]: print u.timeit()
3.05757689476
Iluengo的回答 也向您提供了更多关于为什么您不能在给定数组类型上使用 flatten()ravel() 的信息。

非常感谢您的回答!这是否意味着,flatten()或ravel()所能做到的,hstack()和concatenate()也可以做到,而且更加通用? - xirururu
我会使用 np.array(...).flatten()。 - Golden Lion

9

我同意其他答案中提到的hstack或者concatenate可以在这种情况下完成任务。然而,我想指出的是,即使它“解决”了问题,问题并没有得到适当的解决。

问题在于,即使第二个轴看起来长度不同,在实践中这并不是真的。如果你尝试:

>>> myArray.shape
(2,)
>>> myArray.dtype
dtype('O')    # stands for Object
>>> myArray[0]
[1, 2]

它向您展示,您的数组不是具有可变大小的2D数组(正如您可能认为的那样),它只是对象的1D数组。在您的情况下,元素是list,数组的第一个元素是一个2元素列表,第二个元素是一个1元素列表。
因此,flattenravel无法工作,因为将1D数组转换为1D数组会导致完全相同的1D数组。如果您有一个object numpy数组,它不会关心您放入了什么,它将单独的项目视为未知项目,并且无法决定如何合并它们。
您应该考虑的是,这是否是您的应用程序所需的行为。Numpy数组特别适用于固定大小的数值矩阵。如果您正在处理对象数组,我不明白为什么要使用Numpy而不是普通的Python列表。

我是Python的新手,Numpy提供了许多有用的函数,因此我不需要为像+、-、sum这样的小计算编写冗长的代码... :-) - xirururu
4
@xirururu,我想指出的是,你的数组不是二维的。如果你尝试运行myArray + myArray,结果会是 array([[1, 2, 1, 2], [3, 3]], dtype=object),我很确定这不是你期望的结果。为了使用+-sum,你需要将数组转换为数字类型,并且为此,它应该具有固定的大小。 - Imanol Luengo
谢谢@iluengo。我真的没想到会出现这个问题... :( - xirururu
这是看待问题的一种方式。但是,从用户的角度来看,能够使用flatten和mean是对numpy的变更请求。牢记这个角度非常重要。 - episodeyang

3

np.hstack在这种情况下起作用。

In [69]: np.hstack(myArray)
Out[69]: array([1, 2, 3])

网页内容由stack overflow 提供, 点击上面的
可以查看英文原文,
原文链接