在NumPy中,以下数组形状之间的区别是什么:

51

两个数组形状分别为(442,1)(442,),它们之间有什么区别?

打印这两个数组会得到相同的输出,但是当我使用==检查它们是否相等时,我得到了一个二维向量,如下所示-

array([[ True, False, False, ..., False, False, False],
       [False,  True, False, ..., False, False, False],
       [False, False,  True, ..., False, False, False],
       ..., 
       [False, False, False, ...,  True, False, False],
       [False, False, False, ..., False,  True, False],
       [False, False, False, ..., False, False,  True]], dtype=bool)

有人能解释一下它们之间的区别吗?


5
unutbu 在下面简短的评论中提出了关键洞察。进一步解释:NumPy 数组形状被返回为 Python 元组(tuple),与 Python 列表不同,元组不能直接用单个条目写成:(442) 将只计算为整数 442,而不是像 [422] 一样。在单个元素元组中添加额外的逗号只是 Python 元组语法的一个方面,以将它们与整数区分开来,并没有什么特定与 NumPy 数组有关。 - Jess Riedel
1个回答

60

形状为(442,1)的数组是二维的。它有442行和1列。

形状为(442,)的数组是一维的,由442个元素组成。

请注意,它们的reprs(表示)也应该不同。圆括号的数量和位置有所区别:

In [7]: np.array([1,2,3]).shape
Out[7]: (3,)

In [8]: np.array([[1],[2],[3]]).shape
Out[8]: (3, 1)

请注意,您可以使用np.squeeze来删除长度为1的轴:
In [13]: np.squeeze(np.array([[1],[2],[3]])).shape
Out[13]: (3,)

NumPy广播规则允许在需要时自动添加新轴,在左侧。因此,(442,)可以广播到(1, 442)。长度为1的轴可以广播到任何长度。因此,当您测试形状为(442, 1)和形状为(442, )的数组之间的相等性时,第二个数组会被提升为形状(1, 442),然后两个数组都会扩展其长度为1的轴,使它们都成为广播数组,形状为(442, 442)。这就是为什么当您测试相等性时,结果是一个形状为(442, 442)的布尔数组的原因。
In [15]: np.array([1,2,3]) == np.array([[1],[2],[3]])
Out[15]: 
array([[ True, False, False],
       [False,  True, False],
       [False, False,  True]], dtype=bool)

In [16]: np.array([1,2,3]) == np.squeeze(np.array([[1],[2],[3]]))
Out[16]: array([ True,  True,  True], dtype=bool)

1
谢谢。我是数据挖掘新手,不理解([value],)语法与数组形状正常的([value])语法的区别。那个额外的逗号使事情变得复杂了。 - goelakash
22
(422, ) 中的逗号表示该表达式是一个元组,其中只包含一个元素。如果没有逗号,(422) 将被解析为整数 422。数组的形状始终是一个元组。 - unutbu
4
数组大小分别为 (1,442) 和 (442,) 的数组是相同的吗? - Bikash Gyawali
1
@bikashg 是的,有相同的。 - Florian Courtial

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