当前位置: 首页 > 面试题库 >

通过cython函数与cython方法进行scipy.integrate

慕宜民
2023-03-14
问题内容

我正在尝试研究如何使用cython来加快涉及我定义的类中完成的集成的计算。我试图更好地了解cython如何与用户定义的python类一起工作。我想了解更多有关为什么发生以下描述的错误的信息。

我在名为的文件中有以下cython代码 ex.pyx

from libc.math cimport log
from libc.math cimport sqrt
import scipy.integrate as integ


cdef double integrand_outside(double x):
    """Cython: integrand outside the class"""
    cdef double f = log(x) / sqrt(x)
    return f


cdef class CalcSomething(object):

    def integrate_other(self, double a, double b):
        """This does the integral with the integrand outside the class"""
        return integ.quad(integrand_outside, a, b)[0]

    def integrate_self(self, double a, double b):
        """This does the integral with the integrand inside the class"""
        return integ.quad(self._integrand, a, b)[0]

    def integrate_wrap_self(self, double a, double b):
        """This does the integral with the integrand inside the class"""
        return integ.quad(self.wrap_integrand, a, b)[0]

    def wrap_integrand(self, double x):
        """Python method that wraps _integrand"""
        return self._integrand(x)

    cdef double _integrand(self, double x):
        """Cython: integrand inside the class"""
        cdef double f = log(x) / sqrt(x)
        return f

它显示了scipy.integrate.quad从班级内调用的三种方式

  1. 使用在类外部定义的cython被积函数:(integrate_other确定!)
  2. 使用在类内部定义的cython被积函数:(integrate_self产生错误)
  3. 将在类内部定义的cython被整数函数包装在类内部定义的python函数中:(integrate_wrap_self确定!)

上面的cython代码可以正常编译。现在,我将这些集成方法分别称为

import ex

calcSomething = ex.CalcSomething()

a = 0.001
b = 0.1

calcSomething.integrate_other(a,b)     # works
calcSomething.integrate_wrap_self(a,b) # works
calcSomething.integrate_self(a,b)      # doesn't work

这是回溯:

Traceback (most recent call last):
File "../examples/example.py", line 10, in <module>
print "integrate self =", calcSomething.integrate_self(a,b)   # doesn't work
File "ex.pyx", line 17, in ex.CalcSomething.integrate_self (ex.c:989)
return integ.quad(self._integrand, a, b)[0]
File "/home/alex/Enthought/Canopy_64bit/User/lib/python2.7/site-packages/scipy/integrate/quadpack.py", line 281, in quad
retval = _quad(func,a,b,args,full_output,epsabs,epsrel,limit,points)
File "/home/alex/Enthought/Canopy_64bit/User/lib/python2.7/site-packages/scipy/integrate/quadpack.py", line 345, in _quad
return _quadpack._qagse(func,a,b,args,full_output,epsabs,epsrel,limit)
File "stringsource", line 30, in cfunc.to_py.__Pyx_CFunc_double____CalcSomething____double___to_py.wrap (ex.c:1560)
TypeError: wrap() takes exactly 2 positional arguments (1 given)

这是我的问题:

  • 为什么可以scipy.integrate通过cython函数或python方法(因此现在将实例作为第一个参数)传递却不能作为cython方法传递?错误: TypeError: wrap() takes exactly 2 positional arguments (1 given) 暗示问题出在我想通过cython方法传递的实例参数上?

  • 这个错误是由于我对cython的误解还是对cython的限制引起的scipy

  • 如果我想通过cython加快速度,我打算在类中计算积分(通过在类中也调用积分函数)的计划不是一个好的解决方案吗?披露:实际代码将调用GSL集成函数,而不是scipy


问题答案:

从上面的hpaulj的帮助中:答案是该_integrand方法需要声明为cpdefnotcdef

cpdef double _integrand(self, double x):
    """Cython: integrand inside the class"""
    cdef double f = log(x) / sqrt(x)
    return f


 类似资料:
  • 问题内容: 我正在使用一些Cython扩展模块为项目创建文件。 我已经使这个工作了: 这安装很好。但是,这假定安装了Cython。如果未安装怎么办?我了解这是该参数的用途: 但是,如果尚未安装Cython,则当然会失败: 正确的方法是什么?我只需要在步骤运行后以某种方式导入,但是我需要为了指定值。 问题答案: 您必须包裹在一个,而在,定义为虚函数。这样,可以在不失败的情况下加载脚本。 然后,在处理

  • 准确说Cython是单独的一门语言,专门用来写在Python里面import用的扩展库。实际上Cython的语法基本上跟Python一致,而Cython有专门的&ldquo;编译器&rdquo;先将 Cython代码转变成C(自动加入了一大堆的C-Python API),然后使用C编译器编译出最终的Python可调用的模块。

  • 问题内容: 所以我想通过cython从c调用一些python代码。我设法从c调用cython代码。而且我还可以从cython调用python代码。但是,当我将它们全部加在一起时,会丢失一些东西。 这是我的python代码(): 这是我的cython“ bridge”(): 这是c代码(): 运行此命令时,出现以下异常: 我怀疑缺少的部分: 我还没打电话 我还没有 Cython没有产生任何东西- 不

  • 我正在寻找合并一些cython来加速我的代码。我在Jupyter中运行cython代码时遇到问题。 牢房1: 单元格2: 错误: 但如果我这样做,效果很好。 看起来cdef在Jupyter中的使用方式不同,我如何在Jupyter笔记本中使用cdef?

  • 本文向大家介绍cython 包装DLL:从C ++到Cython到Python,包括了cython 包装DLL:从C ++到Cython到Python的使用技巧和注意事项,需要的朋友参考一下 示例 这展示了一个用Cython包装C ++ dll的简单例子。它将涵盖以下主要步骤: 使用Visual Studio使用C ++创建示例DLL。 用Cython包裹DLL,以便可以在Python中调用它。

  • 我试图包装两个C++类:Cluster和ClusterTree。ClusterTree有一个方法get_current_cluster(),它实例化一个集群对象,并返回对它的引用。ClusterTree拥有集群对象,并在C++中管理其创建和删除。 我用cython包装了Cluster,生成了PyCluster。 PyCluster应该有两种创建方式: 1)通过传入两个数组,这意味着Python应该