首頁
編程語言
C語言|JAVA編程
Python編程
網頁編程
ASP編程|PHP編程
JSP編程
數據庫
MYSQL數據庫|SqlServer數據庫
Oracle數據庫|DB2數據庫
您现在的位置: 程式碼之家 >> 編程語言 >  >> C語言 >> C++ >> 關於C++

C++ 嵌入 Python 實戰:原生 API 與 Boost.Python 兩種方案對比

     編輯:關於C++

方案一:Python C API 原生嵌入

適合輕量級調用,無第三方依賴,但需手動管理引用計數、錯誤檢查、類型轉換,代碼冗長且易出錯。

核心步驟

  1. Py_Initialize() 初始化解釋器。
  2. 定義 C 函數簽名 PyObject* func(PyObject*, PyObject*),用 PyArg_ParseTuple 解析參數,Py_BuildValue 構造返回值。
  3. 構造 PyMethodDef 表,調用 Py_InitModule("HostAPI", methods) 註冊模塊。
  4. PyImport_Import 導入 Python 腳本模塊 (如 helloworld.py)。
  5. 從模塊字典 PyModule_GetDict 獲取函數對象,PyObject_CallObject 調用。
  6. 結果轉換 PyInt_AS_LONG 等,最後 Py_XDECREF 釋放引用,Py_Finalize 清理。

示例交互


// C++ 註冊函數
PyObject* RepeatString(PyObject*, PyObject* args) {
    char* str; int count;
    PyArg_ParseTuple(args, "si", &str, &count);
    for(int i=0;i

方案二:Boost.Python (推薦用於複雜綁定)

提供聲明式語法,自動處理類型轉換、異常傳播、智能指針綁定、繼承體系暴露,代碼極其簡潔。

核心用法


#include 
using namespace boost::python;

class Sample { int v; public: Sample(int v=0):v(v) {} int get() {return v;} void set(int v){this->v=v;} };

BOOST_PYTHON_MODULE(pySample) {
    class_("Sample")
        .def("get", &Sample::get)
        .def("set", &Sample::set);
    register_ptr_to_python>(); // 支持 shared_ptr 自動生命周期
}

int main() {
    Py_Initialize();
    initpySample(); // 模塊初始化函數

    try {
        object main = import("__main__");
        object ns = main.attr("__dict__");
        shared_ptr ptr(new Sample(25));
        ns["sample"] = ptr; // 注入 C++ 對象
        exec_file("sample.py", ns, ns); // 運行腳本
        printf("C++ side: %d, refs: %d\n", ptr->get(), ptr.use_count());
    } catch(error_already_set&) { PyErr_Print(); }

    Py_Finalize();
    return 0;
}

Python 腳本操作 C++ 對象


print "print in python", sample.get()
print sample
sample.set(12345)

輸出結果


print in python 25

print in c: 12345 2
Before finalize
Delete sample address is ...
After finalize

關鍵優勢對比

選型建議

  • 簡單函數調用、極度精簡依賴 → 原生 API。
  • 暴露複雜 C++ 類庫、需異常安全、智能指針管理 → Boost.Python (或現代替代 pybind11,語法相似但僅頭文件、編譯更快)。
  1. 上一篇文章:
  2. 下一篇文章:
Copyright © 程式碼之家 All Rights Reserved
特性原生 APIBoost.Python
樣板代碼量大極小
類/繼承暴露手動實現原生支持
智能指針無register_ptr_to_python
異常傳播手動 PyErr_SetString自動 C++ ↔ Python 轉換
編譯依賴僅 Python.h需 Boost 庫