在哪里可以找到numpy.Where()源代码



我已经找到了numpy.ma.where()函数的源代码,但它似乎正在调用numpy.where)函数,为了更好地理解它,如果可能的话,我想看看。

大多数Python函数都是用Python语言编写的,但有些函数是用更原生的语言(通常是C语言)编写的。

正则Python函数("纯Python")

有一些技术可以用来询问Python本身在哪里定义了函数。可能最便携的使用inspect模块:

>>> import numpy
>>> import inspect
>>> inspect.isbuiltin(numpy.ma.where)
False
>>> inspect.getsourcefile(numpy.ma.where)
'.../numpy/core/multiarray.py'

但这不适用于本机("内置")功能:

>>> import numpy
>>> import inspect
>>> inspect.isbuiltin(numpy.where)
True
>>> inspect.getsourcefile(numpy.where)
TypeError: <built-in function where> is not a module, class, method, function, traceback, frame, or code object

本机("内置")功能

不幸的是,Python没有为内置函数提供源文件的记录。您可以找到哪个模块提供功能:

>>> import numpy as np
>>> np.where
<built-in function where>
>>> np.where.__module__
'numpy.core.multiarray'

Python不会帮助您找到该模块的本机(C)源代码,但在这种情况下,在numpy项目中查找具有类似名称的C源代码是合理的。我发现了以下文件:

numpy/core/src/multirarray/multiarraymodule.c

在那个文件中,我发现了一个定义列表(PyMethodDef),其中包括:

{"where",
(PyCFunction)array_where,
METH_VARARGS, NULL},

这表明C函数array_where就是Python认为的"where"

array_where函数是在同一个文件中定义的,它主要委托给PyArray_Where函数。

简而言之

NumPy的np.where函数是用C编写的,而不是用Python编写的。PyArray_Where是个不错的地方。

首先有两个不同版本的where,一个只使用condition,另一个使用3个数组。

更简单的一个是最常用的,它只是np.nonzero的另一个名称。这将扫描condition阵列两次。一旦使用np.count_nonzero来确定有多少非零条目,这允许它分配返回数组。第二步是填充所有非零条目的坐标。关键是它返回一个数组元组,condition的每个维度都有一个数组。

condition, x, y版本采用三个阵列,它们相互广播。返回数组具有常见的广播形状,元素从xy中选择,如您之前的问题"numpy.where()是如何选择本例中的元素的?

您确实意识到,这些代码中的大部分都是ccython,其中有一个重要的预处理部分。它很难阅读,即使对于有经验的用户来说也是如此。运行各种测试用例并以这种方式了解正在发生的事情更容易。

有几件事需要注意。np.where是一个python函数,python在将每个输入传递给它之前对其进行完全求值。这是条件赋值,而不是条件求值函数。

除非你通过3个形状匹配的数组,或者标量xy,否则你需要对广播有很好的理解。

您可以在numpy.core.multirarray 中找到代码

C:Users<name>AppDataLocalProgramsPythonPython37-32Libsite-packagesnumpycoremultiarray.py是我找到它的地方。

最新更新