解决Pybind11生成的C++扩展模块Binding_py导入失败的ModuleNotFoundError问题
解决Pybind11生成的C++扩展模块Binding_py导入失败的ModuleNotFoundError问题
看起来你遇到的问题核心在于Pybind11定义的模块名和生成的.pyd文件名不匹配,Python是通过.pyd文件的文件名来识别模块的,这和你在PYBIND11_MODULE宏里写的模块名必须严格对应上,咱们一步步来解决:
一、最直接的根治方法:让.pyd文件名和模块名完全一致
你在C++代码里明确定义的模块是Binding_py:
PYBIND11_MODULE(Binding_py, m) { m.doc() = "Example module exposing C++ functions to Python"; m.def("add", &add, "A function that adds two numbers"); m.def("multiply", &multiply, "A function that multiplies two numbers"); }
但生成的.pyd文件却是Binding.cp312-win_amd64.pyd——Python只会去寻找和模块名完全一致的.pyd文件(也就是Binding_py.cp312-win_amd64.pyd),所以必须修改编译配置让输出文件名匹配模块名:
如果你用CMake构建项目,修改CMakeLists.txt里的pybind11_add_module指令,把目标名改成Binding_py:
# 替换原来的Binding为Binding_py,确保和PYBIND11_MODULE定义的模块名一致 pybind11_add_module(Binding_py MODULE 你的C++源文件路径)
重新Clean并Build项目后,生成的.pyd文件名就会和模块名完全匹配,这时候再运行trial.py应该就能成功导入模块了。
二、临时 workaround:用__init__.py映射模块(不推荐长期使用)
如果你暂时不想重新编译,可以在Binds目录下创建一个__init__.py文件,写入以下内容:
# 把现有Binding模块(即当前的.pyd文件)的内容导入到Binding_py命名空间 from Binding import *
这样当你执行import Binding_py时,Python会通过这个__init__.py找到对应的Binding模块,但这只是临时的权宜之计,长期来看还是建议保持模块名和文件名一致,避免后续维护时出现混淆。
三、额外的排查确认点
虽然你的问题主要是文件名匹配问题,但可以再确认以下几点以防其他潜在问题:
- 确认Python版本完全匹配:你的.pyd是
cp312(对应Python 3.12),运行的Python解释器必须是3.12 64位版本,可以执行以下命令验证:python --version python -c "import platform; print(platform.architecture())" - 无需手动添加sys.path(可选):因为你的trial.py和.pyd文件在同一目录,Python默认会把脚本所在目录加入到sys.path中,所以其实可以去掉
sys.path.append(...)这一行,简化代码。 - 确认.pyd文件未损坏:如果编译过程中出现警告或错误,可能会生成无效的.pyd文件,重新Clean再Build项目可以排除这种情况。
备注:内容来源于stack exchange,提问作者Skandan C Y
相关产品推荐
相关产品推荐

