将 python 完全嵌入到 Qt 应用程序中
Fully embedding python into Qt application
我正在寻找一种将 python 完全嵌入到 Qt 应用程序中的方法。有了这个,我的意思是我想构建一个执行 python 代码的 Qt 应用程序,我可以完全分发而不必关心目标机器上安装了哪个 python 版本,也不必询问him/herself.
的未来用户安装 python
我检查了库 PythonQt、PyBind11、Boost.Python 和本地 python 库,它们对 link C++ 到 Python,但他们中的任何一个都做我想做的事。
我在 Linux 中尝试了以下方法,并且我计划在 Windows 和 Mac 中做同样的事情(或者至少是类似的方法):
下载 Python 的源代码(在我的例子中,Python 3.9)。
构建 python.
mkdir build
cd build
../configure --enable-optimizations --enable-shared
make
make install DESTDIR=installed/
将安装的内容复制到我的项目的依赖项文件夹中。安装程序的内容是以下文件夹:
- bin: Contains python executable and some tools like pip.
- include: Contains all of the headers of python.
- lib: Contains the .so libraries and the python modules (if you install a new python module using pip, it will be installed here in python3.9/site-packages/).
- shared: Contains the man entries of python.
有了 Python3.9 版本,我还没有安装任何库,以测试这是否是 C++ 正在调用的 python。
我在我的 .pro 文件中从我的 Qt 应用程序 link 编辑了它,如下所示:
INCLUDEPATH += $$PWD/../dependencies/python3.9/linux/include/python3.9
DEPENDPATH += $$PWD/../dependencies/python3.9/linux/include/python3.9
LIBS += -L$$PWD/../dependencies/python3.9/linux/lib/ -lpython3.9
一旦 linked,我就这样调用 python:
Py_SetPythonHome(L"/link/to/dependencies/python3.9/linux/lib/python3.9/");
Py_SetPath(L"/link/to/dependencies/python3.9/linux/lib/python3.9/");
wchar_t *program = Py_DecodeLocale("", NULL);
if (program == NULL) {
fprintf(stderr, "Fatal error: cannot decode argv[0]\n");
exit(1);
}
Py_SetProgramName(program); /* optional but recommended */
Py_Initialize();
PyRun_SimpleString("import pgmpy");
if (Py_FinalizeEx() < 0) {
exit(120);
}
PyMem_RawFree(program);
在此代码中,我正在导入库 pgmpy
。这个包没有安装在 python 我已经构建的版本中。但是,它安装在我的 python 本地版本中,这意味着它没有使用我构建的 python,即使这是 linked.
是否有任何配置步骤或我遗漏了什么?这可行吗?我对不特定于 Qt 但可以应用于任何 C++ 项目的解决方案更感兴趣,这就是我使用 pybind11 而不是 pythonQt
的原因之一
谢谢。
我终于找到了解决方法。
我从终端执行了 python 解释器,并打印了 sys.path,显示了正确的路径。
然后,在 C++ 中,我将正确的路径附加到 sys.path,删除了错误的路径。
我正在寻找一种将 python 完全嵌入到 Qt 应用程序中的方法。有了这个,我的意思是我想构建一个执行 python 代码的 Qt 应用程序,我可以完全分发而不必关心目标机器上安装了哪个 python 版本,也不必询问him/herself.
的未来用户安装 python我检查了库 PythonQt、PyBind11、Boost.Python 和本地 python 库,它们对 link C++ 到 Python,但他们中的任何一个都做我想做的事。
我在 Linux 中尝试了以下方法,并且我计划在 Windows 和 Mac 中做同样的事情(或者至少是类似的方法):
下载 Python 的源代码(在我的例子中,Python 3.9)。
构建 python.
mkdir build cd build ../configure --enable-optimizations --enable-shared make make install DESTDIR=installed/
将安装的内容复制到我的项目的依赖项文件夹中。安装程序的内容是以下文件夹:
- bin: Contains python executable and some tools like pip. - include: Contains all of the headers of python. - lib: Contains the .so libraries and the python modules (if you install a new python module using pip, it will be installed here in python3.9/site-packages/). - shared: Contains the man entries of python.
有了 Python3.9 版本,我还没有安装任何库,以测试这是否是 C++ 正在调用的 python。
我在我的 .pro 文件中从我的 Qt 应用程序 link 编辑了它,如下所示:
INCLUDEPATH += $$PWD/../dependencies/python3.9/linux/include/python3.9
DEPENDPATH += $$PWD/../dependencies/python3.9/linux/include/python3.9
LIBS += -L$$PWD/../dependencies/python3.9/linux/lib/ -lpython3.9
一旦 linked,我就这样调用 python:
Py_SetPythonHome(L"/link/to/dependencies/python3.9/linux/lib/python3.9/");
Py_SetPath(L"/link/to/dependencies/python3.9/linux/lib/python3.9/");
wchar_t *program = Py_DecodeLocale("", NULL);
if (program == NULL) {
fprintf(stderr, "Fatal error: cannot decode argv[0]\n");
exit(1);
}
Py_SetProgramName(program); /* optional but recommended */
Py_Initialize();
PyRun_SimpleString("import pgmpy");
if (Py_FinalizeEx() < 0) {
exit(120);
}
PyMem_RawFree(program);
在此代码中,我正在导入库 pgmpy
。这个包没有安装在 python 我已经构建的版本中。但是,它安装在我的 python 本地版本中,这意味着它没有使用我构建的 python,即使这是 linked.
是否有任何配置步骤或我遗漏了什么?这可行吗?我对不特定于 Qt 但可以应用于任何 C++ 项目的解决方案更感兴趣,这就是我使用 pybind11 而不是 pythonQt
的原因之一谢谢。
我终于找到了解决方法。
我从终端执行了 python 解释器,并打印了 sys.path,显示了正确的路径。
然后,在 C++ 中,我将正确的路径附加到 sys.path,删除了错误的路径。