摘要 win10系统,编译器为mingw,按照教程封装C++的一个类并用python调用,一步步进行直到最后一步运行python代码时,在python代码中import example
时报错ImportError: DLL load failed while importing _example: The specified module could not be found.
本文记录我的解决方法和其它一些解决思路。
官方文档有完整教程,命令分别为
注意包含自己的头文件目录和库目录,gcc和g++的具体参数见文末的参考链接。
example.c
#include
double My_variable = 3.0;
int my_sum(double a, double b) {
return(a + b);
}
void my_print() {
printf("Hello World!\n");
}
example.i
%module example
%{
extern double My_variable;
extern int my_sum(int n, int m);
extern void my_print();
%}
extern double My_variable;
extern int my_sum(int n, int m);
extern void my_print();
main.py
import example
example.my_print()
print(example.my_sum(1,2))
example.cpp
#include
#include "example.hpp"
void Example::say_hello() {
std::cout << "Hello world!" << std::endl;
}
double Example::my_sum(double a, double b) {
return a+b;
}
example.hpp
class Example {
public:
void say_hello();
double my_sum(double a, double b);
};
example.i
%module example
%{
#include "example.hpp"
%}
%include "example.hpp"
main.py
import example
e = example.Example()
e.say_hello()
print(e.my_sum(1,2))
运行本节开头的3条命令后,不出意外的话,运行3条命令后依次分别生成:
最后运行main.py
后在import example
时报错ImportError: DLL load failed while importing _example: The specified module could not be found.
stackoverflow上有人提到了这个问题,一个解决方法是
I met exactly the same problem after upgraded python to 3.9 on windows . After struggling for hours, I managed to solve it by manually copying some dlls from
***/mingw/bin/
where mingw32-g++ is found to where my***.pyd
is located. I’m sure that***/mingw/bin/
has been appended to %PATH%, but don’t know why python3.9 couldn’t find it.
按照这个方法我把/mingw/bin/
目录下的所有.dll文件全都复制到当前项目目录下确实解决了问题,但文中说只复制了一部分,想到使用静态编译需要用到两个命令-static-libstdc++
和-static-libgcc
,然后测试了一下确实是只需要这两个文件。除了复制文件这一不太优雅的方法以外,只需要在python代码中加上/mingw/bin/
目录即可,完整的python代码如下
import os
os.add_dll_directory('C:/Users/xd15zhn/Documents/mingw64/bin')
import example
e = example.Example()
e.say_hello()
print(e.my_sum(1,2))
但这种方法还是不够优雅,能不能把这两个动态库直接链接到_example.pyd
文件里?我尝试在上面第3条命令后加上-llibgcc_s_sjlj-1 -llibstdc++-6
,但没有用。不知道有没有更优雅的解决方法。
cmake_minimum_required(VERSION 3.14)
project(example)
set(CMAKE_BUILD_TYPE release)
list(APPEND CMAKE_PREFIX_PATH "C:/Users/xd15zhn/Documents/cpplibraries")
# set(MinGW_PATH "C:/Users/xd15zhn/Documents/mingw64/bin")
# set(CMAKE_SHARED_LINKER_FLAGS "-static-libgcc -static-libstdc++")
find_package(Python3 COMPONENTS Interpreter Development REQUIRED)
find_package(Python3 COMPONENTS NumPy REQUIRED)
find_package(SWIG REQUIRED)
message(STATUS "Python3_LIBRARIES: ${Python3_LIBRARIES}")
message(STATUS "Python3_INCLUDE_DIRS: ${Python3_INCLUDE_DIRS}")
message(STATUS "Python3_NumPy_INCLUDE_DIRS: ${Python3_NumPy_INCLUDE_DIRS}")
include(UseSWIG)
set(example_INTERFACE
${PROJECT_SOURCE_DIR}/cppsrc/example.i
)
set(example_SOURCES
${PROJECT_SOURCE_DIR}/cppsrc/example.cpp
)
set_source_files_properties(${example_INTERFACE} PROPERTIES CPLUSPLUS ON)
swig_add_library(example LANGUAGE python SOURCES ${example_INTERFACE} ${example_SOURCES})
target_include_directories(example PUBLIC
${PROJECT_SOURCE_DIR}/cppsrc
${Python3_INCLUDE_DIRS}
${Python3_NumPy_INCLUDE_DIRS}
)
target_link_libraries(example PUBLIC
${Python3_LIBRARIES}
)
下面的代码用于单独生成example.cpp
的动态库来测试自己写的代码是否有问题。
g++ example.cpp -fpic -shared -o example.dll
g++ main.cpp example.dll -o untitled
SWIG doesn’t work on Windows with MinGW-w64 when binding C++ and Python: DLL load failed while importing: The specified module could not be found -stackoverflow
gcc静态编译之-static-libstdc++、-static-libgcc、-static -简书
g++编译详解 -CSDN博客
gcc&g++链接动态库或静态库方法 -CSDN博客
SWIG:Python调用C++(新手保姆级示范) -知乎
The specified module could not be found的解决办法 -CSDN博客