项目结构,用于将cython中的许多c ++类包装到单个共享对象中 [英] project structure for wrapping many c++ classes in cython to a single shared object

查看:229
本文介绍了项目结构,用于将cython中的许多c ++类包装到单个共享对象中的处理方法,对大家解决问题具有一定的参考价值,需要的朋友们下面随着小编来一起学习吧!

问题描述

我在文档,邮寄名单和此问题之间找到了部分答案,但我想要得到一个更直接的答案解决我的细节...

I have found partial answers between the docs, mailing lists, and this question here, but I wanted to get a more direct answer addressing my specifics...

我正在学习cython,试图包装小零件,一个一个图书馆已经使用的是目前包装在boost :: python。我已经贡献了一点点,这个boost包装,并使用它作为一个c ++参考,同时我使用 ZeroMQ Python绑定作为cython引用。

I'm learning cython by trying to wrap small parts, little by little, of a library that I am already using that is currently wrapped in boost::python. I have contributed a tiny bit to this boost wrapper, and am using it as a c++ reference, while at the same time I am using ZeroMQ Python bindings as a cython reference.

我的问题是关于项目结构。该lib的当前boost版本编译为单个 .so ,这是我的目标。我很快发现,你不能直接将多个 .pyx 模块编译为单个 .so 。然后我开始沿着定义 cppclass pxd 文件中的路线,以及他们相应的python导出的实现类在 .pxi 中,并试图将它们包括到一个单独的 pyx 进行编译。虽然它一开始工作,一旦我写了一个更多的问题冲突的多个定义,因为 pxi 包括在不同的地方。

My question is about project structure. The current boost version of this lib compiles to a single .so, and that is my goal. I quickly found out that you cannot directly compile multiple .pyx modules to a single .so. I then started going down the route of defining the cppclass's in pxd files, and their corresponding python exported implementation classes in .pxi, and was trying to include them into a single pyx for compilation. While it worked at first, once I wrote a little more I hit problems with conflicting multiple definitions because of the pxi includes in different places.

我希望听到一个正确的组织方法来解决以下问题和目标:

I would love to hear a proper organizational approach that addresses the following questions and goals:


  • 命名公共类与 cppclass 相同(我现在通过使cppclass位于不同的 pyd 中并使用导入的命名空间以处理类似的名称,ala 使用cimport解决命名冲突

  • 单个 .so 作为编译输出(可接受的方法?

  • 我使用 pyx 方法进入主要的 pyx 为单独,或者应该是 pyx 包含除了只是保持include? / li>
  • 在哪里集中定义将在python中导出的常量?

  • 是否有首选的文件夹结构?现在我在 setup.py 下有一个大的 src 目录。看到这么多 pxi,pxd,pyx 文件时会感到困惑。

  • pxi 完全不必要了?如果没有,我需要使用一个cython风格的ifndef守卫来处理不同模块之间的多重包含?

  • 我知道ZeroMQ python绑定构建多个模块,并使用包方法通过 __ init __。py 这是真的是cython的正确方法吗?

  • Naming the public classes the same as the cppclass (I am doing this now by having the cppclass in a different named pyd and using the imported namespace to handle the similar names, ala Using cimport to resolve naming conflicts)
  • Single .so as the compiled output (acceptable approach?)
  • Do I use the pyx multi-include approach into the main pyx for that alone, or should that main pyx contain anything else beyond just holding the includes?
  • Where to centrally define constants that will be exported in python?
  • Is there a preferred folder structure? Right now I have everything in a big src directory beneath my setup.py. It gets confusing seeing so many pxi, pxd, pyx files.
  • Are pxi completely unnecessary now? If not, do I need to use a cython-style ifndef guard to handle the multiple inclusions between different modules?
  • I know the ZeroMQ python bindings build multiple modules and use the package approach by including them through __init__.py. Is that really the proper approach with cython?

作为参考,我练习重新包装的项目是 PyOpenNI (openni)。这个boost项目需要的模式是在一个地方收集公共对象,然后用源定义一个1对1的头定义,然后有一个巨大的包装器收集所有的定义到单个位置。还有添加的自定义异常处理和实用程序。

For reference, the project I am practicing to re-wrap is PyOpenNI (openni). The pattern this boost project takes is to collect the common objects in one place, and then define a 1-to-1 header definition with the source, and then there is a huge wrapper that collects all of the definitions into the single location. And also the added custom exception handling and utilities.

推荐答案

在等待确定的答案时, 。将 pyx 文件包含到单个 pyx 中用于编译已经工作。

While waiting for a definitive answer, I kept playing around with organizing my code. The including of pyx files into a single pyx for compilation has been working so far.

我的 setup.py 很简单:

ext_modules = [
    Extension(
        "openni", 
        ["src/openni.pyx"], 
        language="c++",
        include_dirs=['src/', '/usr/include/ni'],
        libraries=['OpenNI'],
    )
],

主要 openni.pyx 如下:

include "constants.pyx"
include "exceptions.pyx"
include "context.pyx"
...

我有一个通用的 libopenni.pxd externs到其余的模块。

I have a common libopenni.pxd to provide declaration-only externs to the rest of the modules.

我命名我的 cppclass 声明不同的 pxd pyx 类定义避免名称冲突:

I name my cppclass declarations a different pxd name than the pyx class definitions to avoid name collision:

xncontext.pxd

cdef extern from "XnCppWrapper.h" namespace "xn":
    cdef cppclass Context:
           ...

context.pyx:

from libopenni cimport *
from xncontext cimport Context as c_Context 

cdef class Context:
    cdef c_Context *handle   
        ...

这篇关于项目结构,用于将cython中的许多c ++类包装到单个共享对象中的文章就介绍到这了,希望我们推荐的答案对大家有所帮助,也希望大家多多支持IT屋!

查看全文
登录 关闭
扫码关注1秒登录
发送“验证码”获取 | 15天全站免登陆