你能导入一个 .so 文件吗?

Can you cimport an .so file?

我有一个来自外部库的名为 tissue-classifier.cpython-37m-x86_64-linux-gnu.so 的 .so 文件,我想导入它,以便我可以在我的本地 classes 之一中扩展它。由于我正在扩展 class,我需要使用 cimport 将其作为扩展类型导入,我想知道这是否可能。如果我使用普通的 import 语句,那么我将得到一个 Python 编译版本,它不能用于扩展我当前文件中的 cdef class。

当我尝试 cimport tissue_classifier 文件时,它给我一个错误,即找不到 tissue_classifier.pxd 文件,这是有道理的,因为它在 .so格式。对不起,如果这是一个愚蠢的问题,我只是有一段时间没弄清楚。

不行,不能导入 *.so-file。

如果有人有 C/CPP-backgrounds,那么使用以下模型可能最容易理解 pyx/pxd/so-business:

  • 生成的扩展名(*.so-文件)对应于 C/CPP-world 中的最终工件,它可以是可执行文件、shared-object(*.so)或library/object-filecollection。如果您只是运行生成的程序,这就是您所需要的。例如,您可以使用(并且可能会这样做)一个 CPython-interpreter 而无需构建它或拥有其源代码。以此类推,如果你有一个二进制扩展(*.so),你可以导入并使用它而不必构建它(或者甚至在你的机器上有相应的 pyx-files 或编译器) - 这就是所提供的通过 wheel.
  • *.pyx对应c/cpp-files,里面有函数的定义。如果您想从源代码构建生成的工件,则需要这些文件。在 C/CPP-world 中,此构建过程将通过使用 make 或类似的方式触发。如果您通过 python setup.py install 安装软件包,则需要 pyx-files - 这对应于调用 make.
  • *.pxd 对应于 headers (h/hpp-files):它描述了结果 so-file 中的功能,因此可以重复使用。例如,仅具有 CPython-interpreter 不足以构建扩展 - 必须安装 dev-version 因此还包括 Python.h&Co。出现在机器上。

那么可以做什么呢?


第一种可能:

如果包的作者认为 *.pxd-文件是 public API 的一部分,那么他们可以将相应的 pxd-files next to *.so-files into the installation,所以模块的c-interface可以是used/extended.

如果他们没有将 pxd-file 放入安装中,那么这个 c-interface 很可能是一个实现细节,您不应该使用它,因为它可能会更改,恕不另行通知将来。

但是,可以冒险将必要的 pxd-files 复制到安装中,但首先要确保它是正确的 pxd-version(即与so-file安装中的已构建)。

第二种可能:

确保使用正确 pxd-version 的最简单方法是从源代码构建包,即

  • 正在从 github(主版本或最新版本)下载正确的版本
  • 调用 python setup.py install 或 README 告诉您的操作

现在,不是将 pdx-files 复制到安装中,而是可以通过 cythonize-function 的 include_path 将 include_path 添加到下载的 package-source 或通过添加它到 sys.path.

或者,正如@BeforeFlight 在评论中指出的那样,可以使用 python setup.py develop(或 pip install -e 同一文件夹,以便可以将其卸载),因为它创建了一个 link 将找到 pxd-files 而不是复制数据。


以上解决方案将有助于构建模块,但是分发它是完全不同的事情。