如何使用Cython保持C ++类名不被修改?

时间:2012-04-11 22:12:43

标签: c++ python cython

我有一个名为Foo的C ++类。如果我遵循Cython C++ tutorial,我将需要以不同方式调用Python类,例如PyFoo。 但是我真的需要调用Python类Foo。如何有效地做到这一点?

编辑:我正在尝试连接以前与Boost Python接口的现有C ++库。出于不同的原因,我想测试Cython。 因为使用Boost:使用与C ++相同的名称调用Python Python类,我想继续使用这个命名约定。以不同方式调用类不是Python(CPython)的要求,但它似乎是由Cython强加的,至少在教程中是这样。

我当然可以使用纯python模块来定义一个调用PyFoo的Foo类,但这看起来既乏味又低效。

2 个答案:

答案 0 :(得分:19)

有两种方法可以解决这个问题。

  1. 使用备用名称声明C ++类;原始名称必须用双引号指定:

    cdef extern from "defs.h" namespace "myns":
        cdef cppclass CMyClass "myns::MyClass":
            ...
    

    然后,您可以将MyClass用于您的python类,并将C ++声明称为CMyClass

    请注意,原始名称必须明确包含命名空间(如果它是命名空间)。 Cython模板参数(如果存在)应该在备用名称声明之后。

  2. 在单独的.pxd文件中声明您的C ++类,其名称与.pyx文件的名称不同,然后使用cimport导入它们。

    在cpp_defs.pxd:

    cdef extern from "defs.h" namespace "myns":
        cdef cppclass MyClass:
            ...
    

    在py_wrapper.pyx中:

    cimport cpp_defs as cpp
    
    cdef class MyClass:
        cpp.MyClass *_obj
    

答案 1 :(得分:3)

以下是展示尼基塔方法的完整示例:

cdef extern from "floorplan_geometry.h" namespace "flyby::localize":
    cdef cppclass CFloorplan "flyby::localize::Floorplan":
        int xmin()

cdef class Floorplan:
    cdef CFloorplan* obj_
    def __cinit__(self):
        self.obj_ = new CFloorplan()
    def __dealloc__(self):
        del self.obj_
    def xmin(self):
        return self.obj_.xmin()