简介
python 丰富的模块文件使得python在完成一些功能时非常的方便,在工程中调用python脚本使得效率大大提升。
一、环境配置
python环境配置
要想在vs中调用python脚本,先要将python的解释环境配置到vs工程中。在vs中新建qt工程。然后将python解释器环境拷贝到工程目录下。
得到python解释器环境的方式有很多:
- 复制安装好的整个python环境
- 使用pycharm等三方工具创建虚拟环境
- 从安装好的python环境中提取所需要的环境
本文采用第三中方式
将python安装路径中的include(头文件)和libs(库文件)复制到工程目录下,如下图所示:
工程环境配置
属性 -> c/c++ ->常规 -> 附加包含目录 添加python环境的include文件夹
属性 ->链接器 ->常规 -> 附加库目录 添加python环境的libs文件夹
属性 ->链接器 ->输入-> 附加依赖项 添加python36.lib
然后再工程中包含python.h文头件,编译
避坑
1.编译时报错“错误 LNK1104 无法打开文件“python36_d.lib”,将libs中的python36.lib复制一份,重命名为python36_d.lib
2.编译报错error: expected unqualified-id before ‘;’ token,这是与qt的slots关键字冲突,解决办法是将python中的slot取消宏定义,然后再恢复,如下图
运行环境配置
编译通过后,运行时可能回出现找不到pythonxx.dll情况,因此需要将将python的dll库拷贝到exe所在环境目录下。这里为了方便拷贝了除include和libs的所有文件,如下图所示:
理论上也可以通过配置调试环境变量的方式 项目->属性->调试->环境,进行配置,我没有成功,不知道为啥,大佬可以指点一下:
二、调用python脚本
python脚本
def add(a, b):
c=a+b
return c
c++代码
Py_Initialize();
if (!Py_IsInitialized())
{
printf("error!");
PyErr_Print(); //打印错误
return ;
}
//先获得py文件所在的路径,必须要绝对路径
QString path = QDir::currentPath();
path = path.replace("\\", "/");
qDebug() << path << endl;
path ="sys.path.append('"+ path+"/pycode"+"')";
QByteArray temp = path.toLocal8Bit();
//再设置python运行路径
PyRun_SimpleString("import sys");
PyRun_SimpleString(temp.data());
/**************************/
//如果在py中import了其他模块,应该其他模块也设置到运行路径中
//PyRun_SimpleString("sys.path.append('C:/Users/Administration/Desktop/123/python/Lib/site-packages')");
/**************************/
//导入hello.py模块
PyObject* pModule = PyImport_ImportModule("hello");
if (!pModule) {
printf("Cant open python file!\n");
return;
}
//调用hello脚本
//PyObject_CallFunction(pModule, NULL);
//通过模块获得add函数
PyObject* pFunc = PyObject_GetAttrString(pModule, "add");
if (pFunc)
{
//创建参数列表
PyObject* args = PyTuple_New(2);
PyObject* arg1 = PyLong_FromLong(11111);
PyObject* arg2 = PyLong_FromLong(22222);
PyTuple_SetItem(args, 0, arg1);
PyTuple_SetItem(args, 1, arg2);
PyObject *result = PyObject_CallObject(pFunc,args);
if (result)
{
long a = PyLong_AsLong(result);
qDebug() << "a:" << a << endl;
}
}
//结束,释放python
Py_Finalize();
运行结果
关于打包
- 如果采用之间将python库拷贝到exec的方式,直接使用windeployqt.exe打包,然后将python库拷贝到打包好的文件夹下即可
- 如果采用配置环境变量的方式打包,可以在打包好后的文件夹下添加一个bat脚本,使用set PATH=xxx;%PATH%的方式设置临时环境变量,并在bat中启动软件