以前在開發python和c++混合語言的時候,總是採用簡單的方法快速完成,shell的無比強大助力提供了無需**的方案。但這樣有幾個問題一直無法很優雅的去作,乙個是引數傳遞問題,由於shell不能傳遞太長的引數,所以只能用其它的方法來代替,比如臨時檔案或者系統通訊方法,一點不直接。還有就是效能和系統設計方案的優雅的問題,效能不用說了,程序間的還是每次一起的,優雅木有。所以最近仔細研究了一下這方面的事情,為以後的開發作準備。以下對python和c++混合開發簡稱混合開發。
其實對於混合開發來說,最關鍵的部分是python提供的sdk,它提供了全部的混合開發的功能,有了它你就有了全部。但是,如果光拿sdk進行開發,那麼基本上你會痛不欲生,python的sdk,那叫乙個亂,當然,很多地方是出於效能上的考慮,但對於開發者來說,絕對是乙個惡夢。但是我們有了boost.python,吼吼,終於說到正題了。boost.python幫我們解決了兩個問題,首先乙個,也是最重要的,解決了python sdk混亂的引用計數問題,提供了一致性的解決方案。其次,提供了基於c++模板技術的,統一的,高效能的封裝。
先來看乙個例子:考慮這樣乙個場景,對於使用python的web框架進行開發的人,django是乙個簡單實用的工具。如果我們用django進行前端開發,使用django的模板和orm工具,在後端我們可以使用c++來進行一些高效能的處理。比如進行一些大計算量的工作,然後把結果放入到資料庫中供前端django使用。一種方法可能是完全採用python來開發,但是對於大計算量來說,python實在不是乙個好主意。如果使用c++來開發,那麼資料庫怎麼處理,我們可以借用django的orm,這樣可以省去維護兩個資料庫操作的麻煩。
我們使用boost.python來處理python嵌入c++的問題,例子**:
try
catch(error_already_set const &)
catch (...)
這樣我們就簡單的嵌入了python**並取回了結果.
關於如何用boost.python進行混合開發的方法,網上有無數的教程,不再贅述了,說說在測試學習過程中遇到的問題。
1.首先的乙個問題,就是關於多執行緒開發,boost.python是不支援多執行緒的,原因在於python sdk自身對多執行緒的處理也不好,在查詢了相關的資料後發現,python在某乙個版本以後,提供了一些多執行緒方面的支援,大致是這個樣子:在初始化的時候加入
py_initialize();
pyeval_initthreads();
pyeval_releasethread(pythreadstate_get());
結束的時候加入:
pygilstate_ensure();
py_finalize();
先寫乙個簡單的類:
class pythreadstatelock
~pythreadstatelock(void)
private:
pygilstate_state state;
};
?
1pythreadstatelock lock;
2.關於boost.python,在boost.python2.0版本,也就是目前最新的boost1.46.1提供的版本,沒有提供對py_finalize()的支援,也就是說,在你整個程序的內部,實際上只共享了乙個python直譯器,這樣你就沒有辦法通過py_finalize()來釋放python所占用的記憶體,而對於python直譯器的內部的記憶體管理機制而言,一但python直譯器分配了記憶體,就會被cache起來而不會立刻釋放。這個意思就是說在一些大型的專案中我們需要關注python解釋的記憶體使用問題。實際測試過程中發現,python直譯器也會釋放一些不用的記憶體,但這個過程很慢。如果你需要記憶體理論上可以用gc.collect來手工釋放,但實測效果不明顯.這個問題目前沒有好的解決方法.
3.對於boost.python沒有支援的功能,可以使用python原生的sdk來解決,同時我們也需要對python sdk的相關系統有所了解,了解其真實的執行方式,這樣才能真正知道我們作了什麼,沒作什麼.感謝一下開源專案,原始碼之前,了無秘密.
4.關於django的,django出於效率的考慮,cache了大部分可以cache的東西,但這對於只是想嵌入使用一下orm的混合開發人員來說,其實沒太大意義,反而如果資料庫內容量比較大的時候,會導致python直譯器占用大量的記憶體而得不到釋放.這個的解決方法是在每次使用django orm 使用過後,對其cache進行清空處理,**:
from django.utils.datastructures import sorteddict
cache.handled = {}
cache.loaded = false
當然如果你確實需要orm的cache,比如說經常性的匯出資料,那麼可以不清.
5.其實boost.python也可以進行c++**的python嵌入,可能這種模式用的更多一些,只是這裡沒有用到.
總的來說,我們得到了一種進行混合開發的方法,我們可以嵌來嵌去的,嵌來嵌去的,來嵌去的,嵌去的,去的,的...
c 和Python混合程式設計
1.設定環境 1 在vs的附加包含目錄中新增python的include路徑 2 在vs linker的附加庫目錄中新增python的libs路徑 3 注意,如果安裝的python是64位的,那麼vs工程也要是一直對應的x64活動平台,否則會報 無法解析的外部符號 imp py initialize...
c和c 混合使用
我們編寫 經常需要c和c 混合使用,為了使 c 和 c 保持互相相容的過程呼叫介面,需要,為了簡化,從而定義了兩個巨集方面我們使用 1.在 c 裡加上 extern c 作為符號宣告的一部分。2.begin decls 和 end decls 在c語言 中標頭檔案中,充斥著下面的 片段 begin ...
混合使用C和C
legacy 參考最近在看專案 經常看到header file中,開頭 ifdef cplusplus extern c endif cplusplus 中間包裹 includes,typedefs,以及function prototypes。不懂就要問,去查了下,發現這是為了告知編譯器,以c語言的...