c嵌入python
『壹』 求助 關於c程序中嵌入python的問題
嵌入
與python的擴展相對,嵌入是把Python解釋器包裝到C的程序中。這樣做可以給大型的,單一的,要求嚴格的,私有的並且(或者)極其重要的應用程序內嵌Python解釋器的能力。一旦內嵌了Python,世界完全不一樣了。
C調用python中的函數:
hw.py:
#coding=utf8
def hw_hs(canshu):
return canshu
if __name__ == "__main__":
ccss = "I am hw"
print hw_hs(ccss)
helloWorld.py:
#coding=utf8
import hw
def hello():
ccss = "I am helloWorld"
return hw.hw_hs(ccss)
if __name__ == "__main__":
print hello()
testcpypy.c:
//#include "testcpypy.h"
#include <Python.h>
#include <stdio.h>
#include <stdlib.h>
int main()
{
//初始化Python
Py_Initialize();
if (!Py_IsInitialized()) {
printf("Py_Initialize");
getchar();
return -1;
}
//執行python語句
PyRun_SimpleString("import sys");
PyRun_SimpleString("sys.path.append('./')");
PyObject *pMole = NULL;
PyObject *pFunc = NULL;
PyObject *reslt =NULL;
//載入python模塊
if(!(pMole = PyImport_ImportMole("helloWorld"))) {
printf("PyImport_ImportMole");
getchar();
return -1;
}
//查找函數
pFunc = PyObject_GetAttrString(pMole, "hello");
if ( !pFunc || !PyCallable_Check(pFunc) )
{
printf("can't find function [hello]");
getchar();
return -1;
}
//調用python中的函數
reslt = (PyObject*)PyEval_CallObject(pFunc, NULL);
//printf("function return value : %d\r\n", PyInt_AsLong(reslt));
//將python返回的對象轉換為C的字元串
char *resltc=NULL;
int res;
res = PyArg_Parse(reslt, "s", &resltc);
if (!res) {
printf("PyArg_Parse");
getchar();
return -1;
}
printf("resltc is %s", resltc);
getchar();
//釋放內存
Py_DECREF(reslt);
Py_DECREF(pFunc);
Py_DECREF(pMole);
//關閉python
Py_Finalize();
return 0;
}
編譯:
gcc -o testcpypy testcpypy.c -IC:\Python27\include -LC:\Python27\libs -lpython27 ---C:\Python27為python安裝目錄
或:
gcc -c testcpypy.c -IC:\Python27\include
gcc -o testcpypy.exe testcpypy.o -LC:\Python27\libs -lpython27
執行結果:
帶參數的情況:
#include "callpydll.h"
#include "Python.h"
#include <stdio.h>
#include <stdlib.h>
#include <string.h>
#include <stdarg.h>
int callhello(char *instr, char *outstr)
{
PyObject *pMole = NULL;
PyObject *pFunc = NULL;
PyObject *reslt = NULL;
PyObject *pParm = NULL;
char *resltc = NULL;
int resltn;
int res;
char *helloWorld = "TestIM_ProtocBuf";
char *im_account = "aaaa";
char *auth_code = "aaaa";
char *im_uid = "aaaa";
char *proxy_topic = "";
//初始化Python
Py_Initialize();
if (!Py_IsInitialized()) {
printf("Py_Initialize");
getchar();
return -1;
}
//執行python語句
PyRun_SimpleString("import sys");
PyRun_SimpleString("sys.path.append('./')");
//載入python模塊
if(!(pMole = PyImport_ImportMole(helloWorld))) {
printf("PyImport_ImportMole");
getchar();
return -2;
}
//查找函數
pFunc = PyObject_GetAttrString(pMole, "login_proxy_body_serialize");
if ( !pFunc || !PyCallable_Check(pFunc) )
{
printf("can't find function [hello]");
getchar();
return -3;
}
//參數轉換C --> python, 參數必須是元組(一個參數也是,否則會失敗!!!坑啊)
pParm = Py_BuildValue("(ssss)", im_account, auth_code, im_uid, proxy_topic);
//調用python中的函數
reslt = (PyObject*)PyEval_CallObject(pFunc, pParm);
//將python返回的對象轉換為C的字元串
res = PyArg_ParseTuple(reslt, "si", &resltc, &resltn);
if (!res) {
printf("PyArg_Parse");
getchar();
return -4;
}
printf("resltn is %d", resltn);
memcpy(outstr, resltc, strlen(resltc)+1);
//釋放內存
Py_DECREF(reslt);
Py_DECREF(pFunc);
Py_DECREF(pMole);
Py_DECREF(pParm);
//關閉python
Py_Finalize();
return 0;
}
int main() {
int i;
char *dais = "iammain";
char res[10240];
memset(res,'\0',sizeof(res));
i = callhello(dais, res);
if(0 != i) {
printf("Notify:error");
getchar();
return -1;
}
printf("result is %s", res);
getchar();
return 0;
}
『貳』 怎樣把Python代碼嵌入到C程序
步驟1:安裝Python開發包
由於需要訪問Python/C API,首先安裝Python開發包。
在Debian,Ubuntu或Linux Mint中:
在CentOS,Fedora或RHEL中:
安裝成功後,Python頭文件在/usr/include/python2.7。根據Linux發行版的不同,確切的路徑可能是不相同的。例如,CentOS 6中是/usr/include/python2.6。
步驟2:初始化解釋器並設置路徑
C中嵌入Python的第一步是初始化Python解釋器,這可以用以下C函數完成。
初始化解釋器後,需要設置你的C程序中要導入的Python模塊的路徑。例如,比如你的Python模塊位於/usr/local/moles。然後使用以下C函數調用來設置路徑。
步驟3:數據轉換
C中嵌入Python最重要的方面之一是數據轉換。從C中傳遞數據到Python函數,需要首先將數據從C數據類型轉換到Python數據類型。Python/C API提供各種函數來實現這。例如,轉換C字元串到Python字元串,使用PyString_FromString函數。
另外一個類似函數PyInt_FromLong,將C中long數據類型轉換為Python int。每個Python/C API函數返回一個PyObject類型的引用。
步驟4:定義一個Python模塊
當你想嵌入Python代碼到另一種語言如C,該代碼需要被寫成Python模塊,然後用另一種語言「導入」。所以讓我們來看看如何在C中導入Python模塊。
為了進行說明,我們實現一個簡單的Python模塊例子如下:
以上的Python函數有一個字元串作為參數並返回兩個重復的字元串。例如,如果輸入字元串是「cyberpersons」,該函數返回'cyberpersonscyberpersons'。此模塊文件命名為「printData.py」並將它放在前面聲明的Python模塊目錄中(/usr/local/moles)。
步驟5:載入一個Python模塊
現在你已經定義了Python模塊,是時候在C程序中載入它了。導入模塊的C代碼看起來像這樣:
步驟6:構建函數的參數
當載入一個模塊時,可以調用模塊中定義的Python函數。通常,我們需要傳遞一個或多個參數到一個Python函數。我們必須構建一個Python元組對象,它包括Python函數中的參數。
在我們的例子中,printData函數定義帶一個參數的模塊。因此,我們構建一個大小是一的Python元組對象如下。我們可以使用PyTuple_SetItem設置元組對象的每個項。
我們已經成功構建一個參數傳遞到函數調用,是時候從C程序調用python函數了。
步驟7:調用Python函數
一旦成功創建Python元組對象作為函數參數,我們可以調用一個帶參數的Python函數。為此,通過使用PyObject_GetAttrString首先獲得模塊中定義的函數的引用,然後使用PyObject_CallObject調用該函數。例如:
步驟8:錯誤檢查
避免運行時錯誤的常見方法是檢查函數的返回值並根據返回值採取適當的行動。類似於C程序中的全局變數errno,Python/C API提供一個全局指示符,它報告最後發生的錯誤。當Python/C API函數失敗,全局指示符設置為指示錯誤,並且PyErr_Print可以用於顯示相應的人類可讀的trackback。例如:
在你的應用程序中,你可以輕松地將各種錯誤檢查。
這里是完整的C程序,它如本教程描述的嵌入Python代碼。
步驟9:編譯和執行
保存以上代碼到finalCode.c,並且鏈接Python庫(-lpython2.7)編譯該代碼。根據發行版的不同,可能使用不同的版本(例如,-lpython2.6)。
『叄』 求助,C++中嵌入Python,無法導入自定義模塊
將當前目錄加入path中
PyRun_SimpleString("sys.path.append('./')");
pMole = PyImport_ImportMole("pytest");
無法import是因為路徑不對啊。你需要通過sys.path里加入你要import的模塊的路徑就可以解決了。
這和C++沒有關系。與嵌入式沒有關系。另外有些安裝包,它是解壓後運行,所以也需要注意目錄的問題。
嵌入python與命令行使用python執行,結果是一樣的。使用的都是cpython的解釋器。所以不用擔心有什麼不同。
以前還在c++ builder里用過python的程序。也是一樣。
『肆』 在c++裡面嵌入python應該怎麼調試
Python容易擴展和嵌入。Python提供的許多標准模塊支持C或者C++介面。Python和C可以一起工作,它可以嵌入到C或者C++的應用程序當中,因此可用Python語言為應用程序提供腳本介面,由於支持跨語言開發。
可用Python設計概念化應用程序,並逐步移植到C,使用前不必用C重寫應用程序。(Jython使Python可以和Java一起工作,使開發者可以在Python裡面調Java的包,也可以在Java裡面使用Python的對象。還有更妙的,由於Jython的解釋器完全用Java編寫,因此可以在支持Java的任何平台上部署Python程序,甚至WEB瀏覽器也可以直接運行Python腳本。)
提出問題在某個C++應用程序中,我們用一組插件來實現一些具有統一介面的功能,我們使用Python來代替動態鏈接庫形式的插件,這樣可以方便地根據需求的變化改寫腳本代碼,而不是必須重新編譯鏈接二進制的動態鏈接庫。Python強大的功能足以勝任,但是有一些操作系統特定的功能需要用C++來實現,再由Python調用。所以,最基礎地,我們需要做到:
1. 把Python嵌入到C++應用程序中,在C++程序中調用Python函數和獲得變數的值;
2. 用C++為Python編寫擴展模塊(動態鏈接庫),在Python程序中調用C++開發的擴展功能函數。
『伍』 請教高手,我在C/C++中嵌入python,用PyImport
#include<iostream>
#include<Python.h>
usingnamespacestd;
voidHelloWorld();
voidAdd();
voidTestTransferDict();
voidTestClass();
intmain()
{
cout<<"StartingTest..."<<endl;
cout<<"HelloWorld()-------------"<<endl;
HelloWorld();
cout<<"Add()--------------------"<<endl;
Add();
cout<<"TestDict-----------------"<<endl;
TestTransferDict();
cout<<"TestClass----------------"<<endl;
TestClass();
system("pause");
return0;
}
//調用輸出"HelloWorld"函數
voidHelloWorld()
{
Py_Initialize();//使用python之前,要調用Py_Initialize();這個函數進行初始化
PyObject*pMole=NULL;//聲明變數
PyObject*pFunc=NULL;//聲明變數
pMole=PyImport_ImportMole("Test001");//這里是要調用的Python文件名
pFunc=PyObject_GetAttrString(pMole,"HelloWorld");//這里是要調用的函數名
PyEval_CallObject(pFunc,NULL);//調用函數,NULL表示參數為空
Py_Finalize();//調用Py_Finalize,這個和Py_Initialize相對應的.
}
//調用Add函數,傳兩個int型參數
voidAdd()
{
Py_Initialize();
PyObject*pMole=NULL;
PyObject*pFunc=NULL;
pMole=PyImport_ImportMole("Test001");//Test001:Python文件名
pFunc=PyObject_GetAttrString(pMole,"add");//Add:Python文件中的函數名
//創建參數:
PyObject*pArgs=PyTuple_New(2);//函數調用的參數傳遞均是以元組的形式打包的,2表示參數個數
PyTuple_SetItem(pArgs,0,Py_BuildValue("i",5));//0---序號i表示創建int型變數
PyTuple_SetItem(pArgs,1,Py_BuildValue("i",7));//1---序號
//返回值
PyObject*pReturn=NULL;
pReturn=PyEval_CallObject(pFunc,pArgs);//調用函數
//將返回值轉換為int類型
intresult;
PyArg_Parse(pReturn,"i",&result);//i表示轉換成int型變數
cout<<"5+7="<<result<<endl;
Py_Finalize();
}
//參數傳遞的類型為字典
voidTestTransferDict()
{
Py_Initialize();
PyObject*pMole=NULL;
PyObject*pFunc=NULL;
pMole=PyImport_ImportMole("Test001");//Test001:Python文件名
pFunc=PyObject_GetAttrString(pMole,"TestDict");//Add:Python文件中的函數名
//創建參數:
PyObject*pArgs=PyTuple_New(1);
PyObject*pDict=PyDict_New();//創建字典類型變數
PyDict_SetItemString(pDict,"Name",Py_BuildValue("s","WangYao"));//往字典類型變數中填充數據
PyDict_SetItemString(pDict,"Age",Py_BuildValue("i",25));//往字典類型變數中填充數據
PyTuple_SetItem(pArgs,0,pDict);//0---序號將字典類型變數添加到參數元組中
//返回值
PyObject*pReturn=NULL;
pReturn=PyEval_CallObject(pFunc,pArgs);//調用函數
//處理返回值:
intsize=PyDict_Size(pReturn);
cout<<"返回字典的大小為:"<<size<<endl;
PyObject*pNewAge=PyDict_GetItemString(pReturn,"Age");
intnewAge;
PyArg_Parse(pNewAge,"i",&newAge);
cout<<"TrueAge:"<<newAge<<endl;
Py_Finalize();
}
//測試類
voidTestClass()
{
Py_Initialize();
PyObject*pMole=NULL;
PyObject*pFunc=NULL;
pMole=PyImport_ImportMole("Test001");//Test001:Python文件名
pFunc=PyObject_GetAttrString(pMole,"TestDict");//Add:Python文件中的函數名
//獲取Person類
PyObject*pClassPerson=PyObject_GetAttrString(pMole,"Person");
//創建Person類的實例
PyObject*pInstancePerson=PyInstance_New(pClassPerson,NULL,NULL);
//調用方法
PyObject_CallMethod(pInstancePerson,"greet","s","HelloKitty");//s表示傳遞的是字元串,值為"HelloKitty"
Py_Finalize();
}
#test.py
defHelloWorld():
print"HelloWorld"
defadd(a,b):
returna+b
defTestDict(dict):
printdict
dict["Age"]=17
returndict
classPerson:
defgreet(self,greetStr):
printgreetStr
#printadd(5,7)
#a=raw_input("EnterToContinue...")
結果:
注意兩點:
若編譯Debug版,請將C:/Python26/libs下的python26.lib復制一份改名為python26_d.lib
test.py 記得放項目的當前目錄。
測試通過
『陸』 LINUX下要在C中嵌入Python,編譯的時候怎樣解決庫的連接問題
一個helloworld測試編譯器能運行.但代碼里加入 include <python.h>就報錯,經查找,python.h在/usr/include/python3.4里,
『柒』 【Python】【C++】C++嵌入Python的一些問題,模塊無法導入
無法import是因為路徑不對啊。你需要通過sys.path里加入你要import的模塊的路徑就可以解決了。
這和C++沒有關系。與嵌入式沒有關系。另外有些安裝包,它是解壓後運行,所以也需要注意目錄的問題。
嵌入python與命令行使用python執行,結果是一樣的。使用的都是cpython的解釋器。所以不用擔心有什麼不同。
以前還在c++ builder里用過python的程序。也是一樣。
『捌』 python怎樣嵌入c
用c語言編寫一個動態庫,提供兩個函數,兩個數的整形求和,兩個浮點數的求和。取名為mylib.c。
將c函數文件編譯成so動態庫。運行gcc mylib.c -fPIC -shared -o libtest.so命令,在目錄下可以看到生成的庫文件libtest.so。
Python調用so庫文件。首先導入ctypes,其次用CDLL載入so文件,最後調用對應的函數。將python代碼保存到pydemo.py中。
執行python pydemo.py查看運行結果。
眾多python培訓視頻,盡在python學習網,歡迎在線學習!
『玖』 怎麼樣才能在c程序中嵌入python而不用依賴系統安裝的python而運行。也說是說怎麼把pyth
這個思路不是很行得通。。建議題主再思考一下程序結構。
為何要在C程序中嵌入python呢?
windows下,如果是一個獨立的python腳本,可以用py2exe轉換成一個可獨立運行的exe。因此如果能把python代碼分離出來,問題就簡單了。
『拾』 怎樣才能在c程序中嵌入python而不用依賴系統安裝的python而運行。...
這個思路不是很行得通。。建議題主再思考一下程序結構。
為何要在C程序中嵌入python呢?
windows下,如果是一個獨立的python腳本,可以用py2exe轉換成一個可獨立運行的exe。因此如果能把python代碼分離出來,問題就簡單了。