我将创建C库,并希望使用Cython创建Python包装器。

现在,我已经编译并捆绑了mylib.a文件(C文件),并且我想将我的库中的方法包装在Cython中。

我已经成功创建了.pyx.pxd文件,并且可以使用python setup.py build_ext命令进行构建。当我尝试在pypi上发布它时,出现了我的问题。如果我运行setup.py,创建wheel并发布它,我可以从pypi下载它-但我不能运行import mylib

我为此阅读了很多在线教程。他们中很少有人表明他们的C代码是在用户端编译的。我的代码库将由许多文件构成,我希望将已经构建的C代码作为.a文件提供。

我的文件结构(仅重要文件):

/ lib
    - mylib.a
    - *.h files (for mylib.a)
- setup.py
/ mylib
    - mylib.pyx
    - cmylib.pxd
    - __init__.py

我的__init__.py文件(导入从pip下载的程序包后,它将在此处引发错误):
from . import mylib

我的setup.py(仅重要参数-我认为):
setup(name='mylib'
      packages=['mylib'],
      ext_modules = [Extension(
          name="mylib",
          sources=["mylib/mylib.bycython.c"],
          include_dirs = [numpy.get_include(), "lib/"],
          extra_objects=["lib/mylib.a"])],
        "build_ext": build_ext
      }
)

(我使用mylib.bycode.c中的cython在python setup.py build_ext之前构建mylib.pyx。根据this的文章,这将使安装程序包更快,并且不需要用户具有相同的cython版本。)

也许值得一提-构建软件包后,我得到了mylib的.so文件。如果我将其复制到/mylib目录,则可以从父目录进行import mylib并使用mylib.mylib.say_hello()访问我的方法。但是,它不适用于从pip(在其他PC上)安装的软件包,我也不想使用mylib.mylib

如果我应该提供更多信息-请告诉我。

编辑:

我在GitHub上的项目(我之前混淆了名称,所以这里是真实的项目):https://github.com/franiis/statr-python

我想从say_hello()成功运行statr.pyx方法(其他方法可能无法使用)。

我知道代码存在一些问题,但是我想首先拥有一个可以解决所有问题的核心。要构建项目,请使用build_script.shupload_script.sh创建转轮并发布。

最佳答案

setup.py中有几个问题。

  • setup.py不会编译链接到库的文件。这意味着它必须手动编译。
  • 链接到库是一个预编译的静态链接存档。它不是可移植的,不能分发到用于构建它的GCC/glibc的确切版本以外的任何版本。
  • setup.py并未构建cython扩展代码。对.pyx/.pxd的更改将不会反射(reflect)在软件包中。

  • 尝试类似的东西:
    from setuptools import setup, find_packages, Extension
    from Cython.Build import cythonize, build_ext
    
    extensions = [Extension(
              name="statr._ext",
              sources=["statr/_ext.pyx", "lib/mylib.c"],
              depends="lib/mylib.h",
              include_dirs=[numpy.get_include(), "lib/"]
    ]
    
    setup(name='statr'
          packages=find_packages(),
          ext_modules=cythonize(extensions),
          build_ext: build_ext
          }
    )
    

    通过以上操作,扩展名将为statr._ext。 pyx的名称应为_ext.pyx
    mylib.c将被构建并通过setup.py链接到扩展名。 mylib.c所需的任何其他编译器指令都应添加到扩展中。

    包名称将为statr。您应该从_ext导入想要从顶层statrd模块的__init__.py中可用的任何内容,例如
    from ._ext import my_cython_function
    

    关于python - 准备基于C的Cython软件包以在pypi上发布,我们在Stack Overflow上找到一个类似的问题:https://stackoverflow.com/questions/49471084/

    10-12 18:36