`numpy.array(value)` 的意思是什么?

3
numpy.array(value)会在value为intfloatcomplex类型时评估为true。该结果似乎是一个无形状数组(numpy.array(value).shape返回())。
将上述内容进行如下重塑numpy.array(value).reshape(1)能够正常工作,而numpy.array(value).reshape(1).squeeze()则可以将其反转,并再次生成无形状的数组。
这种行为背后的原理是什么?有哪些使用案例需要注意此行为呢?

你从一个标量得到另一个标量,这有什么不合理的地方呢? - Mad Physicist
此外,调用squeeze时缺少括号。 - Mad Physicist
如果您不想得到一个标量,可以传递 ndmin=1 - Mad Physicist
1
据我理解,标量不是数组。但是type(np.array(11))numpy.ndarray。我的问题不在于我不理解标量或数组的含义,而是numpy将标量归类为数组类型。 - fabianegli
2
这是一个0D数组,不是无形状的,其形状是零长度元组()。这并没有什么不合逻辑的地方。它也非常有用,例如,如果您正在编写一个希望能够处理数组和标量的函数。 - Paul Panzer
1个回答

3

当你创建一个零维数组,例如np.array(3)时,你得到的是一个在99.99%的情况下表现为数组的对象。你可以检查它的基本属性:

>>> x = np.array(3)
>>> x
array(3)
>>> x.ndim
0
>>> x.shape
()
>>> x[None]
array([3])
>>> type(x)
numpy.ndarray
>>> x.dtype
dtype('int32')

到目前为止还不错。这背后的逻辑很简单:只需将任何类似数组的对象包装在 np.array 的函数调用中,就可以以相同的方式处理它,无论它是数字、列表还是数组。

需要记住的一件事是,当您索引一个数组时,索引元组必须具有 ndim 或更少的元素。所以你不能这样做:

>>> x[0]
Traceback (most recent call last):
  File "<stdin>", line 1, in <module>
IndexError: too many indices for array

相反,你必须使用一个零大小的元组(因为 x[] 是无效的语法):

>>> x[()]
3

您也可以将数组用作标量:
>>> y = x + 3
>>> y
6
>>> type(y)
numpy.int32

将两个标量相加会生成一个dtype的标量实例,而不是另一个数组。话虽如此,在99.99%的情况下,您可以像使用x一样使用本示例中的y,因为dtypes继承自ndarray。由于np.add将其包装在array中,所以Python中的int 3并不重要。y = x + x将产生相同的结果。

这些示例中xy之间的一个区别是,x在官方上被认为不是标量:

>>> np.isscalar(x)
False
>>> np.isscalar(y)
True

索引问题可能会使您计划索引任何类似于数组的对象受阻。您可以通过在构造函数中提供ndmin=1参数或使用reshape轻松解决它:

>>> x1 = np.array(3, ndmin=1)
>>> x1
array([3])

>>> x2 = np.array(3).reshape(-1)
>>> x2
array([3])

我通常建议使用前一种方法,因为它不需要对输入的维度有先前的了解。

进一步阅读:


2
你可以始终使用 ndim 元组进行索引。 - hpaulj
@hpaulj。感谢您的提示。我已更新语言。 - Mad Physicist
谢谢您的回答和提供进一步阅读的链接。这让我度过了一个充满教育意义的晚上。 - fabianegli
我刚刚偶然发现了另一种使用item函数从numpy数组中获取标量值的方法:x.item()。灵感来自于这里,当我在研究如何使用numpy.savez()时。 - fabianegli

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