C++程序調用python3
今天想做一個簡單的管理密碼的小程序,由於最近了解了下Python,就想用Python來寫。但是看了看Python的界面庫用法有感覺有點麻煩,所以還不如直接使用MFC寫寫界面,關於csv的文件處理部分使用Python來做,這樣可能會簡單些。
版本
vs使用2013版本
python使用3.6
notepad++配置python環境
https://www.cnblogs.com/huangsitao/p/10323198.html
VS中配置Python環境
1.在C++中調用Python需要包含“Python.h”頭文件,通過everything搜索找到"Python.h",默認路徑為C:\Users\Administrator\AppData\Local\Programs\Python\Python36-32\include
2.找到lib文件,我的是Python36.lib,默認路徑為C:\Users\Administrator\AppData\Local\Programs\Python\Python36-32\libs
3.將include目錄和libs目錄拷貝一份保存到sln同級目錄(因為在這個解決方案中我要寫C++調用Python的程序)
4.在vs中對應的工程上右鍵->屬性,C/C++->常規->附加包含目錄填寫include路徑,鏈接器->常規->附加庫目錄填寫lib路徑,鏈接器->輸入->附加依賴項填寫python36.lib
5.main.cpp中編寫下面代碼,編譯沒有問題說明配置成功
1 #include<Python.h> 2 int main() 3 { 4 return 0; 5 }
開始寫代碼
初始化
Py_Initialize(); //載入Python的內建模塊並添加系統路徑到模塊搜索路徑中。無返回值
檢查是否初始化成功
Py_IsInitialized();
添加當前路徑到系統路徑中
PyRun_SimpleString("import sys"); PyRun_SimpleString("sys.path.append(‘./‘)");
PyRun_SimpleString為執行Python語句的函數。
加載python腳本文件
首先要寫好pytest.py文件放到exe同級目錄下。
pMoudle為NULL說明加載失敗,失敗的可能原因有:
1.找不到pytest.py文件,可能未將pytest.py文件拷貝到exe同級目錄或者為設置當前路徑為系統路徑
2.pytest.py腳本有語法錯誤(我的就是這種原因,2.0和3.0的python語法不同,直接將別人的pytest代碼拷貝過來未檢查導致失敗)
PyObject* pModule = PyImport_ImportModule("pytest");
獲取到函數
PyObject* func = PyObject_GetAttrString(pModule, "add");
檢查函數是否獲取成功
if (!PyCallable_Check(func)) { std::cout << "not find add function." << std::endl; return -1; }
設置調用函數的參數
調用Python函數,參數和返回值都必須為元組
PyObject* args = PyTuple_New(2); PyObject* arg1 = PyLong_FromLong(4); PyObject* arg2 = PyLong_FromLong(3); PyTuple_SetItem(args, 0, arg1); PyTuple_SetItem(args, 1, arg2);
調用函數
PyObject* pValue = PyObject_CallObject(func, args);
輸出返回值
if (pValue != NULL) { printf("Result of call: %ld\n", PyLong_AsLong(pValue)); Py_DECREF(pValue); }
釋放資源
Py_Finalize();
完整代碼
1 #include<iostream> 2 #include<Python.h> 3 4 int main() 5 { 6 Py_Initialize(); 7 // 檢查初始化是否成功 8 if (!Py_IsInitialized()) { 9 return -1; 10 } 11 // 添加當前路徑,可以避免導入模塊輸入全路徑 12 PyRun_SimpleString("import sys"); 13 PyRun_SimpleString("print (‘---import sys---‘)"); 14 PyRun_SimpleString("sys.path.append(‘./‘)"); 15 // 載入名為pytest的腳本 16 PyObject* pModule = PyImport_ImportModule("pytest"); 17 if (!pModule) // 加載模塊失敗 18 { 19 std::cout << "[ERROR] Python get module failed." << std::endl; 20 system("pause"); 21 return 0; 22 } 23 std::cout << "[INFO] Python get module succeed." << std::endl; 24 25 PyObject* func = PyObject_GetAttrString(pModule, "add"); 26 if (!PyCallable_Check(func)) 27 { 28 std::cout << "not find add function." << std::endl; 29 system("pause"); 30 return -1; 31 } 32 PyObject* args = PyTuple_New(2); 33 PyObject* arg1 = PyLong_FromLong(4); 34 PyObject* arg2 = PyLong_FromLong(3); 35 PyTuple_SetItem(args, 0, arg1); 36 PyTuple_SetItem(args, 1, arg2); 37 PyObject* pValue = PyObject_CallObject(func, args); 38 if (pValue != NULL) 39 { 40 printf("Result of call: %ld\n", PyLong_AsLong(pValue)); 41 Py_DECREF(pValue); 42 } 43 else 44 { 45 Py_DECREF(func); 46 Py_DECREF(pModule); 47 PyErr_Print(); 48 fprintf(stderr, "Call failed\n"); 49 return 1; 50 } 51 Py_Finalize(); 52 system("pause"); 53 return 0; 54 }
參考
https://docs.python.org/2/extending/embedding.html
https://www.cnblogs.com/yanzi-meng/p/8066944.html
C++程序調用python3