首页 > 解决方案 > numpy 作者如何决定是否将函数放入 numpy.* 与 numpy.ndarray.* 中?

问题描述

我觉得我在这里错过了一些统一的主题。有几个观察结果我在上下文中遇到了麻烦。

  1. flatten() 在 numpy.ndarray.* 中,但是 flatten() 实际上是不合适的,这对我来说似乎有点奇怪,因为它是一个对象方法,而不是一个库函数。

  2. 那么,如果允许对象方法返回副本,那么为什么 np.repeat() (不合适)不仅仅是 np.ndarray.* 中的对象方法?

  3. 另一方面,非对象方法 numpy.reshape 是就地的......这种趋势似乎与我的预期有点相反。

  4. np.random.randn() 为要生成的数组的维度采用多个位置参数,而 np.zeros 采用包含维度的单个位置参数元组。是否有一个原因?

我只是想了解导致这些选择的设计决策,这样我就不会在如何调用这些函数时反复犯愚蠢的错误。

谢谢。

标签: pythonnumpy

解决方案


In [495]: x = np.arange(12).reshape(3,4)      # reshape((3,4)) also                                                         
In [496]: x.flatten?                                                                                   
Docstring:
a.flatten(order='C')
Return a copy of the array collapsed into one dimension.

ravel方法和函数是“等价的”:

In [497]: x.ravel?                                                                                     
Docstring:
a.ravel([order])
Return a flattened array.
Signature: np.ravel(a, order='C')
Docstring:
Return a contiguous flattened array.

A 1-D array, containing the elements of the input, is returned.  A copy is

仅在需要时制作。

用你的术语来说,flattenout-of-placeravel不是。或者用numpy's术语来说,ravel通常产生 a view,而不是 a copy

的实际代码np.ravel是:

if isinstance(a, np.matrix):
    return asarray(a).ravel(order=order)
else:
    return asanyarray(a).ravel(order=order)

如果参数不是数组,则将其转换为一个。然后使用该方法。

这种模式很常见。该函数asarray在需要时执行一个操作,然后将操作委托给该方法。

np.reshapex.reshape遵循这个模式。有一种x.shape=...形式是真正的in-place行动。他们尽可能返回 a view(他们不会改变元素的总数)。这view共享数据,但有自己的shapestrides.

resize是两者之间有显着差异的函数/方法对之一。我们用的不多。

repeat功能与方法相同。因为它通常会更改元素的数量,所以repeat(两种形式)都会返回一个带有自己数据的新数组。它不返回view.

sum是另一个返回新数组的对。它改变了元素的数量,所以 aview是不可能的。

至于randn,它的文档解释了差异。将形状指定为元组可能是首选的“标准”,但这种randn行为是不寻常的。新代码的建议替代方案standard_normal采用size元组。reshape接受任何一个。

虽然正常的元组语法是(1,2,3),但()实际上是可选的;它是标记元组的逗号。它在 1 元素元组中是必需的,例如。(1,). 在索引中x[(1,2)]x[1,2]是相同的,将 a 传递tuplex.__getitem__.

python和pythonnumpy都有悠久的历史。过去做出的选择现在仍然以一种或另一种方式与我们同在。提炼代码很慢;添加功能比删除它们更容易。


推荐阅读