繁体   English   中英

Python C 模块扩展版本不兼容吗?

[英]Is Python C module extension version incompatible?

我在 Python 3.6 中编译了一个 python c 模块扩展。 它在 Python 3.6 环境中运行良好,但在 Python 3.7 和 3.8 环境中不起作用,出现错误cannot import name 'cygrpc'

我想知道这是预期的行为吗? 如果是,是什么原因呢。

这取决于扩展的编译方式以及它使用的 Python C API 接口。 但是是的,通常必须编译 C 扩展以针对特定版本的 Python 在不知道如何创建扩展模块的情况下,我认为它需要重新编译。

通常,Python C API 会在每个版本中更改。 如果该更改破坏了您的扩展程序中的某些内容,自然而然,您必须针对新的 API 接口更新您的扩展程序。 但是,即使您的更改源代码兼容(不需要更改源代码来支持新的 Python 版本),也并不意味着编译后的二进制文件必须兼容。 这就是二进制接口 (ABI) 发挥作用的地方。

另请参阅:稳定的应用程序二进制接口,其中描述了这背后的原因:

原因主要是结构定义的演变,其中添加新字段或更改字段类型可能不会破坏 API,但会破坏 ABI。 因此,每个 Python 版本都需要重新编译扩展模块 [...]

还提到了二进制文件跨版本兼容的有限情况:

自 Python 3.2 起,已声明 API 的一个子集以保证稳定的 ABI。 希望使用此 API(称为“受限 API”)的扩展模块需要定义 Py_LIMITED_API。 一些解释器的细节会从扩展模块中隐藏起来; 作为回报,构建了一个无需重新编译即可在任何 3.x 版本 (x>=2) 上运行的模块。

因此,如果您仅使用稳定 API 的一部分并定义Py_LIMITED_API ,则编译后的模块可能无需重新编译即可跨 Python 版本兼容。

暂无
暂无

声明:本站的技术帖子网页,遵循CC BY-SA 4.0协议,如果您需要转载,请注明本站网址或者原文地址。任何问题请咨询:yoyou2525@163.com.

 
粤ICP备18138465号  © 2020-2024 STACKOOM.COM