伙伴云客服论坛»论坛 S区 S软件开发 查看内容

0 评论

0 收藏

分享

C++如何调用简单的python程序

目录

    一、根本环境的搭建二、直接在C++里面调用执行python语句三、调用python脚本文件里面的定义函数
      调用不含参数的函数调用含多个参数的函数
    总结


一、根本环境的搭建

首先,用vs创建一个win32的控制台应用程序项目(vs2017及以上怎么创建百度一下就晓得了)。
然后配置好python的环境变量(把include文件夹加到包含目录,libs文件夹加到库目录,最好还把include文件夹加到附加包含目录)。
如下图所示:
C++如何调用简单的python程序-1.jpg

C++如何调用简单的python程序-2.jpg

最后,把python36.libs文件加到依赖项(假设是debug编译,要重命名python36.libs为python36_d.libs,然后加到依赖项)
如下图所示。
C++如何调用简单的python程序-3.png

C++如何调用简单的python程序-4.png


二、直接在C++里面调用执行python语句

搭建好一中的环境之后,在源文件里面新建一个cpp文件,cpp里面的代码如下。
代码很简单,应该一看就懂了吧。
#include <Python.h>
#include <stdio.h>
#include <iostream>
using namespace std;
int main()
{
        //***python调用***//
        //直接在C++里面执行python语句
        void usePythonWorld();
        usePythonWorld();
        system("pause");
}
void usePythonWorld()//调用无参数函数
{
        //初始化python模块:用来分配python解释器所使用的全局资源
        Py_SetPath(L"D:/chengxuanzhuang/anaconda/envs/python3.6/Lib");
        Py_Initialize();
        if (!Py_IsInitialized())// 检查初始化是否胜利
        {
                cout << "初始化失败" << endl;
                Py_Finalize();
        }
        //直接调用python语句(没有胜利)
        PyRun_SimpleString("print('in python'\n)");
        Py_Finalize();

}
需要注意的地方是,在使用PyRun_SimpleString之前,一定要使用 Py_Initialize()初始化Python。

三、调用python脚本文件里面的定义函数


调用不含参数的函数

搭建好一中的环境之后,在源文件里面新建一个cpp文件,cpp里面的代码如下。
代码很简单,应该一看就懂了吧。
#include <Python.h>
#include <stdio.h>
#include <iostream>
using namespace std;
int main()
{
        //***python调用***//
        //调用无参数python函数
        bool InvokeNonParasFuncByAPI(string module, string func);
        InvokeNonParasFuncByAPI("PythonGreet", "Hello");
        system("pause");
}
bool InvokeNonParasFuncByAPI(string module, string func)
{
        Py_SetPath(L"D:/chengxuanzhuang/anaconda/envs/python3.6/Lib");
        Py_Initialize();
        if (!Py_IsInitialized())
        {
                return false;
        }
        try
        {
                //将当前目录切换到python脚本放置的目录,因为初始化到了python的全局资源下,所以只能只用python语句
                PyRun_SimpleString("import sys\n");
                PyRun_SimpleString("sys.path.append('./')");//这个一个简单的执行python脚本命令的函数,由于途径是'./',所以python脚本要放在这个项目的根目录

                //调用pyhton脚本
                PyObject* moduleName = PyUnicode_FromString(module.c_str());
                PyObject* pModule = PyImport_Import(moduleName);
                if (!pModule)
                {
                        cout << "Import Module Failed" << endl;
                        return false;
                }
                PyObject* pFunc = PyObject_GetAttrString(pModule, func.c_str());//调用脚本里面的函数
                if (!pFunc || !PyCallable_Check(pFunc)) //这里面的这个函数是用来判断方法是否有效
                {
                        cout << "Get Function Failed!" << endl;
                        return false;
                }
                PyObject* pResult = PyObject_CallObject(pFunc, nullptr);//使用python脚本里面的函数
                if (!pResult)
                {
                        cout << "Get Result of Function Failed!" << endl;
                        return false;
                }
        }
        catch (...)
        {
                PyErr_Print(); //假设出错会打印出错误
                PyErr_Clear();
                Py_Finalize();
                return false;
        }
        Py_Finalize();
        return true;
}
调用含一个参数的函数
搭建好一中的环境之后,在源文件里面新建一个cpp文件,cpp里面的代码如下。
代码很简单,应该一看就懂了吧。
C++如何调用简单的python程序-5.png

其中的demo_test是python脚本文件名,注意不是demo_test.py。最后把这个python脚本文件和cpp文件放在同一个文件夹下(注意不是放在源文件里,而是找到cpp文件所在的文件夹,放到这个文件夹里。
如下。假设是在项目里直接创建的python文件,会自动寄存到这个文件夹下)
C++如何调用简单的python程序-6.png

不出意外,就可以运行这个cpp文件了。

调用含多个参数的函数

搭建好一中的环境之后,在源文件里面新建一个cpp文件,cpp里面的代码如下。
代码很简单,应该一看就懂了吧。
#include <Python.h>
#include <stdio.h>
#include <iostream>
#include <vector>
using namespace std;
int main()
{
        //***python调用***//
        //调用含参数的python函数
        vector<int> paras;
        paras.push_back(3);
        paras.push_back(4);
        bool InvokeFuncbyAPI(string module, string func, vector<int> paras);
        InvokeFuncbyAPI("PythonCalc", "Add",paras);
        system("pause");
}
bool InvokeFuncbyAPI(string module, string func,vector<int> paras)
{
        Py_SetPath(L"D:/chengxuanzhuang/anaconda/envs/python3.6/Lib");
        Py_Initialize();
        if (!Py_IsInitialized())
        {
                return false;
        }
        try
        {
                //将当前目录切换到python脚本放置的目录,因为初始化到了python的全局资源下,所以只能只用python语句
                PyRun_SimpleString("import sys\n");
                PyRun_SimpleString("sys.path.append('./')");//这个一个简单的执行python脚本命令的函数,由于途径是'./',所以python脚本要放在这个项目的根目录

                //调用pyhton脚本
                PyObject* moduleName = PyUnicode_FromString(module.c_str());
                PyObject* pModule = PyImport_Import(moduleName);
                if (!pModule)
                {
                        cout << "Import Module Failed" << endl;
                        return false;
                }
                PyObject* pFunc = PyObject_GetAttrString(pModule, func.c_str());//调用脚本里面的函数
                if (!pFunc || !PyCallable_Check(pFunc)) //这里面的这个函数是用来判断方法是否有效
                {
                        cout << "Get Function Failed!" << endl;
                        return false;
                }
                PyObject* pResult = nullptr; //创建一个获取结果的python数据构造
                PyObject* args = PyTuple_New((int)paras.size());//建立一个寄存入参的python数据构造
                for (int i = 0; i < (int)paras.size(); i++)
                {
                        PyTuple_SetItem(args, i, PyLong_FromLong(paras)); //将C++的参数转化为python的参数
                }
                pResult = PyObject_CallObject(pFunc, args);
                if (!pResult)
                {
                        cout << "Get Result of Function Failed!" << endl;
                        return false;
                }
                cout << "Result = " << PyLong_AsLong(pResult) << "by python api" << endl;

        }
        catch (...)
        {
                PyErr_Print();//假设出错会打印出错误
                PyErr_Clear();
                Py_Finalize();
                return false;
        }
        Py_Finalize();
        return true;
}

总结

以上为个人经历,希望能给大家一个参考,也希望大家多多支持网站。

回复

举报 使用道具

全部回复
暂无回帖,快来参与回复吧
本版积分规则 高级模式
B Color Image Link Quote Code Smilies

凉凉
注册会员
主题 23
回复 19
粉丝 0
|网站地图
快速回复 返回顶部 返回列表