boost.python入門教程 —-python 嵌入c++

來源:互聯網
上載者:User

boost.python 中 python 嵌入c++ 部分,網上找到的中文資料似乎都有些過時了,

如 boost.python學習筆記 http://edyfox.codecarver.org/html/boost_python.html

在boost.python版本2中,提供更加簡潔易用的介面,我們可以使用從而

代替原始的PyRun_SimpleString等等python c 轉換api.

 

關於python與C++混合編程,事實上有兩個部分

  1. extending   所謂python 程式中調用c/c++代碼, 其實是先處理c++代碼, 預先產生的動態連結程式庫, 如example.so,  而在python代碼中import example;即可使用c/c++的函數 .
  2. embedding  c++代碼中調用 python 代碼.

兩者都可以用 python c 轉換api,解決,具體可以去python官方文檔查閱,但是都比較繁瑣.

對於1,extending,常用的方案是boost.python以及swig.

swig是一種膠水語言,粘合C++,PYTHON,我前面的圖形顯示二叉樹的文章中提到的就是利用pyqt作介面,

調用c++代碼使用swig產生的.so動態庫.

而boost.python則直接轉換,可以利用py++自動產生需要的wrapper.關於這方面的內容的入門除了boost.python

官網,中文的入門資料推薦

 

用Boost.Python + CMake + wxPython構建跨語言GUI程式<一> 

 

http://www.cppblog.com/skyscribe/archive/2009/08/09/92686.html

一共3個系列吧,他的部落格上還有cmake的內容,本文的環境也將使用cmake編譯,可供參考.

對於2 似乎swig就不提供支援了,swig 不僅僅支援 python調用c/c++,還支援許多其它進階語言調用c++, 但是它不支援python 嵌入c++.

下面僅僅介紹2 embedding, 事實上embedding 比 extending 簡單的多:)

本將會給出具體執行個體代碼以及環境配置方法.有些只是為了簡單,並不是最好的配置方案,

如cmake的使用.

  • 環境配置 

   我的工作環境是ubuntu8.04,gcc4.24,cmake2.6,boost1.4,python2.6.

       如果你在windows下工作就不用往下看了.

       boost.python似乎還不支援python3 所以個人推薦使用python2.6,當然ubuntu8.04內建的python2.5

        也可以的.

      1.python2.6 的安裝

             去官網下載python2.6,解壓縮,

             ./configure --enable-shared;make; sudo make install

             標頭檔應該會預設安裝到/usr/local/include/python2.6.

             注意第一步 ./configure --help可以查看協助選項,如你想設定安裝到什麼路徑,

             特別注意 --enable-shared選項產生動態連結程式庫,libpython2.6.so 

             這個是我們下面需要的一定要有這個選項! 預設會產生到/usr/local/lib下,你直接./configure 

             的話則不會產生動態連結程式庫.

          2. cmake  安裝

              sudo apt-get insall cmake即可,也可以去官網下載安裝最新的cmake2.8

          3. boost   安裝

             去官網下載boost.1.4.2 解壓縮

             ./bootstrap.sh  --help

             ./bootstrap.sh --show-libraries  #會顯示你有哪些庫可以安裝

             這裡解釋一下,因為boost是模板庫,很多都只需要標頭檔,不需要編譯安裝,但是有些庫是需要安裝的如

             regex,python, 等等,你可以查看一下選擇自己需要安裝的庫.

              我選擇了全部安裝,預設是全部安裝.

              ./bootstrap.sh --prefix=/usr/local/boost1.4

              這樣會將標頭檔安裝到 /usr/local/boost1.4/include

              庫檔案安裝到 /usr/local/boost1.4/lib

              然後 

              ./bjam install

               注意不加install的話檔案不會拷貝到你指定的安裝路徑的.

             然後你可以設定一下環境變數,如BOOST_ROOT,BOOST_LIB

             下面我實驗的時候直接寫的安裝路徑,如 /usr/local/boost1.4/include

  • 直接用python,c 轉換api 如何?.

         看一個最簡單的例子

        

#include <Python.h>
int
main(int argc, char *argv[])
{
Py_Initialize();
PyRun_SimpleString("from time import time,ctime\n"
"print 'Today is',ctime(time())\n");
Py_Finalize();
return 0;
}

       假設這個程式命名為a.cc,如何編譯它呢.無外乎要能找到python的標頭檔和動態連結程式庫.如下:

       g++ -I /usr/local/include/python2.6 -lpython2.6 -o a a.cpp

       ./a

        Today is Sun Nov 15 17:25:25 2009

  • boost.python的支援  

         使用boost.python需要以下步驟

 

  1. #include <boost/python.hpp>
  2. 調用Py_Initialize()  來開啟解譯器 並且產生  _main_ 模組 .
  3. 使用該解譯器調用 Python C API .注意當前你一定不要最後調用Py_Finalize了結束解譯器 ,這個問題可能會在以後版本中改掉. 當然你可以在這些步驟中有其它的C++代碼.

     還是直接看代碼吧,boost.python提供了3種調用python代碼的方法,

     eval, exec, exec_file,

     分別對應

     計算運算式值,

     執行python語句,

     執行python 文本如a.py.

     而boost::python::object的使用,使得調用python中的函數異常的簡單.

     下面的代碼,示範了exec,exec_file,object的使用,基本上覆蓋了所有常見的需求.

      首先寫一個簡單的python 檔案 ,

      simple.py

     

def foo(i = 4):
  return i + 2008

 

      寫一個C++的代碼

      embedding.cc

 

#include <iostream>
using namespace std;
#include <boost/python.hpp>
using namespace boost::python;

int main(int argc, char *argv[])
{
  Py_Initialize();

  object main_module = import("__main__");
  object main_namespace = main_module.attr("__dict__");
  exec("hello = file('hello.txt', 'w')\n"
       "hello.write('Hello world!')\n"
       "hello.close()",
       main_namespace);
  exec("result = 5 ** 2", main_namespace);
  int five_squared = extract<int>(main_namespace["result"]);
  cout << "The five_squeared caculated by python is " << five_squared << endl;

   // Load the sys module.
  object sys = import("sys");

  // Extract the python version.
  std::string version = extract<std::string>(sys.attr("version"));
  std::cout << version << std::endl;

 
 //要求simple.py與可執行檔在相同路徑下! 運行ok
  object simple = exec_file("simple.py",main_namespace, main_namespace);
  //dict global;
  //object result = exec_file("simple.py", global, global);
  object foo = main_namespace["foo"];
  int val = extract<int>(foo(5));
  cout << "Python has caculated foo as " << val << endl;

  return 0;
}

 如何編譯這個程式呢,其實就是能找的python, 以及boost.python的標頭檔和庫檔案.我採用了cmake,管理.

 最簡單的在相同代碼路徑下,建立一個檔案CMakeLists.txt,寫入以下內容,注意你可能需要根據自己的安裝路徑進行

 更改.

project(Embedding) #隨便起一個工程名稱

#boost.python,python標頭檔路徑
include_directories(/usr/local/boost1.4/include /usr/local/include/python2.6)

link_directories(/usr/local/boost1.4/lib /usr/local/lib)  #boost.python,python動態連結程式庫路徑

add_executable (embedding embedding.cc)  #源檔案embedding.cc 產生可執行檔embedding
target_link_libraries(embedding libboost_python.so libpython2.6.so) #可執行檔依賴與這兩個庫

 

 如果你配置好環境變數,或者標頭檔庫在預設的尋找位置,或者應用ln可能不需要這麼繁瑣,但是這樣是一個可行的方案.

cmake .

make

./embedding

         The five_squeared caculated by python is 25
   2.6.2 (r262:71600, Nov 14 2009, 14:18:33)
   [GCC 4.2.4 (Ubuntu 4.2.4-1ubuntu4)]
   Python has caculated foo as 2013

 

      

 

 

相關文章

聯繫我們

該頁面正文內容均來源於網絡整理,並不代表阿里雲官方的觀點,該頁面所提到的產品和服務也與阿里云無關,如果該頁面內容對您造成了困擾,歡迎寫郵件給我們,收到郵件我們將在5個工作日內處理。

如果您發現本社區中有涉嫌抄襲的內容,歡迎發送郵件至: info-contact@alibabacloud.com 進行舉報並提供相關證據,工作人員會在 5 個工作天內聯絡您,一經查實,本站將立刻刪除涉嫌侵權內容。

A Free Trial That Lets You Build Big!

Start building with 50+ products and up to 12 months usage for Elastic Compute Service

  • Sales Support

    1 on 1 presale consultation

  • After-Sales Support

    24/7 Technical Support 6 Free Tickets per Quarter Faster Response

  • Alibaba Cloud offers highly flexible support services tailored to meet your exact needs.