Warning: file_get_contents(/data/phpspider/zhask/data//catemap/2/python/342.json): failed to open stream: No such file or directory in /data/phpspider/zhask/libs/function.php on line 167

Warning: Invalid argument supplied for foreach() in /data/phpspider/zhask/libs/tag.function.php on line 1116

Notice: Undefined index: in /data/phpspider/zhask/libs/function.php on line 180

Warning: array_chunk() expects parameter 1 to be array, null given in /data/phpspider/zhask/libs/function.php on line 181
Python sklearn内部访问cython类和函数_Python_Scikit Learn_Cython - Fatal编程技术网

Python sklearn内部访问cython类和函数

Python sklearn内部访问cython类和函数,python,scikit-learn,cython,Python,Scikit Learn,Cython,我感兴趣的是测试sklearn中定义的许多内部类和函数(例如,可能会将print语句添加到treebuilder中,以便查看树是如何构建的)。然而,由于许多内部构件都是用Cython编写的,我想了解在Jupyter笔记本中测试功能的最佳实践和工作流程 例如,我设法从模块导入了类。我甚至能够构造它,但无法调用任何方法。我该怎么做才能在Python中调用和测试cdef类及其方法 %%cython from sklearn.tree import _utils s = _utils.Stack(10

我感兴趣的是测试sklearn中定义的许多内部类和函数(例如,可能会将print语句添加到treebuilder中,以便查看树是如何构建的)。然而,由于许多内部构件都是用Cython编写的,我想了解在Jupyter笔记本中测试功能的最佳实践和工作流程

例如,我设法从模块导入了类。我甚至能够构造它,但无法调用任何方法。我该怎么做才能在Python中调用和测试cdef类及其方法

%%cython 
from sklearn.tree import _utils
s = _utils.Stack(10)
print(s.top())
# AttributeError: 'sklearn.tree._utils.Stack' object has no attribute 'top'

为了能够使用内部类的c接口,必须解决一些问题

第一个问题(如果您的ssklearn版本>=0.21.x,请跳过):

在0.21.x版sklearn使用隐式相对导入(如Python2)之前,使用Cython(IPython3中的默认值)编译它是不起作用的-因此<0.21.x版(即
%Cython-2
)或更好的版本需要设置
language_level=2
,应该更新
scikit learn

第二个问题:

我们需要包括numpy头的路径。让我们来看一个更简单的版本:

%%cython 
from sklearn.tree._tree cimport Node
print("loaded")
它失败了,没有显示错误“命令'gcc'失败,退出状态为1”-但真正的原因可以在终端中看到,其中gcc输出其错误消息(而不是笔记本):

致命错误:numpy/arrayobject.h:没有这样的文件或目录 编译终止

\u tree.pxd
使用numpy API,因此我们需要提供numpy头的位置

这意味着我们
include_dirs=[numpy.get_include()]
Extension
定义。有两种方法可以通过
-I
选项在
%%cython
-magic中执行此操作:

%%cython -I <path from numpy.get_include()>
...
够了

最后但并非最不重要的一点:

pxd文件必须存在于安装中,以便我们能够对其进行cimport。这是来自
sklearn.tree
子包的pxd文件的情况,正如人们在本地看到的(考虑到这一点,这似乎或多或少是一个随机决定,背后没有策略):

但对于其他一些cython扩展,尤其是。现在,对于您的示例来说,这是一个问题:

%%cython 
# requires numpy headers 
from sklearn.tree._utils cimport Stack
s = Stack(10)
print(s.top())
未能进行Cythonization,因为来自
邻居的
\u utils.pxd
.pxd

...
from sklearn.neighbors.quad_tree cimport Cell
...
安装中不存在的

在本文中,将详细描述这种情况,您的构建选项是(如链接中所述)

  • 将pdx文件复制到安装
  • 使用
    pip install-e从下载的源代码重新安装
  • 操作相应的本地
    setup.py
    -文件后,从下载的源代码重新安装

另一个选择是要求sklearn的开发人员在安装中包含pxd文件,这样不仅可以进行构建,还可以进行分发。

我想你指的是Cython,而不是CPython。@juanpa.arrivillaga,很抱歉造成混淆,刚刚修改了问题。要访问cdef功能,您需要cimport而不是导入。@ead,
来自sklearn.tree。_utilscimport Stack
失败,编译错误为
self.\u compile(obj、src、ext、cc_args、extra_postargs、pp_opt gcc失败,退出状态代码为1
。由于缺乏cython和setuptools经验,对我来说这是一个相当大的挑战,您能否进一步阐述如何解决依赖关系?我知道pdx是定义文件,pyx是实现文件,_utils.pxd使用Neights.qu中的Cell结构ad_tree.pxd.在上面列出的三个选项中,当你说安装时,是指在sklearn根目录下运行
python setup.py develope
,还是在submodue上运行特定的本地setup.py,比如说
sklearn.tree
文件夹。真遗憾,这三个选项中的任何一个都没有起作用,是吗?@B.Mr.W.不确定,你的想法是什么问题是:您已经卸载了当前版本,克隆了sclearn存储库并遵循了?如果仍然存在问题,最好提出一个新问题,因为注释对于解决问题来说并不太好。在打开新线程之前,请再问一个问题。我找到了所有依赖项,如
neights.Cell
,并将其直接添加到_-utils.pxd and_utils.pyx,因此最终应该没有依赖项/引用问题。然后我根据您的建议创建了自己的最小setup.py。它编译时没有任何问题,我成功生成了一个_utils.so文件。但是,当我使用%%cython magic运行代码时,它肯定会正确调用堆栈,因为如果您不通过测试,它会抱怨但是,它无法找到像top这样的属性,有什么想法吗?@B.Mr.W。如果没有一个精确的定义,这必然会成为一系列误解,并浪费每个人的时间,因此我再次拒绝在评论中排除问题。几分钟前,我很幸运地让它工作起来,以替换
堆栈=堆栈(10)
使用
cdef Stack Stack=Stack(10)
,您的代码应该可以工作。不太清楚为什么。
%%cython 
# requires numpy headers 
from sklearn.tree._utils cimport Stack
s = Stack(10)
print(s.top())
...
from sklearn.neighbors.quad_tree cimport Cell
...