---
# System prepended metadata

title: 在c++使用svm模型並執行實時預測

---

作者 : 林哲丞
email : snoopy195011@gmail.com

## 目標
在C++執行python的一些東西可以使用pybind11或是boost.python這兩種套件,這兩種套件在使用上會比較方便,原先打算使用boost.python,但是嘗試一段時間後發現有點太困難,因此改用pybind11


## 系統設置

1. 安裝python,版本3.8(64bit),並將其路徑加到電腦的環境變數
2. 安裝pybind11,版本2.11,並將其路徑加到電腦的環境變數


3. pybind11支援的編譯器最低規格是visual studio 2017 (v141),所以專案至少要使用visual studio2017以上的版本
![](https://hackmd.io/_uploads/SyeRmMwyn2.png)
pybind11的documentation : https://pybind11.readthedocs.io/en/stable/

4. 打開Visual Studio專案的屬性頁面,確認平台工具組是visual studio 2017(v141)且Windows SDK為10.0
![](https://hackmd.io/_uploads/SyIa_D13h.png)


5. 打開Visual Studio專案的屬性頁面的組態管理員,將組態設為Debug模式,平台選擇x64
![](https://hackmd.io/_uploads/rkEsNPJ2h.png)


6. 打開Visual Studio專案的屬性頁面將python和pybind11的檔案路徑加入include
![](https://hackmd.io/_uploads/Bkq2XvJh3.png)

7. 打開Visual Studio專案的屬性頁面新增python連結器的路徑
![](https://hackmd.io/_uploads/HkyEEvJ3h.png)

8. 安裝Visual C++ Redistributable
用途: 內含有一些.dll檔,可以使c++和python成功進行互動.若沒安裝,電腦會抓不到python檔案,並擲回例外狀況
官方下載網址 : https://learn.microsoft.com/en-us/cpp/windows/latest-supported-vc-redist?view=msvc-170


## 程式部分
### model_loader.py
用途 :　將要預測的力感測器資料以list的形式傳入svm()函式,該函式會將資料丟進之前已經提前訓練好的svm模型,並回傳預測結果,預測結果以python裡面的int的形式回傳
![](https://hackmd.io/_uploads/BJOxKnx3n.png)

### main.cpp
(以下的截圖並非在kithara電腦擷取,因此有紅線)

用途: 在c++裡面初始化一些python和pybind11相關的工具

![](https://hackmd.io/_uploads/BJ7EhDJn2.png)
#include <Python.h> 和 "svm_wrapper.h"

![](https://hackmd.io/_uploads/BySWswk2h.png)
Py_SetProgramName -> 想要和c++互動的python檔案名稱
Py_Initialize() -> 初始化python的解釋器

PyRun_SimpleString("import sys")
PyRun_SimpleString("sys.path.append('C:/Users/Lab816/.....')")  ->讓程式知道要去哪邊找python檔案

auto model_loader = py::module::import("model_loader") -> 將python檔案抓進C++專案
以上5行程式順序不可調換

### svm_wrapper.cpp
![](https://hackmd.io/_uploads/H1CFTvynn.png)

predict_svm()的parameter分別代表要引入的python程式的object以及要進行預測的資料,資料以python的list形式傳入

auto p = model_loader.attr("svm")(data); -> 呼叫python程式中名為svm的函式,data為svm函式的parameter, 並且回傳該函式的return值.

int result = pybind11::cast<int>(p); 雖然在python中svm函式回傳int, 但是python的int和C++的int並不一樣,因此須進行資料型態的轉換,並將預測結果return出去,方便後續程式進行處理
    
## 結果
目前成功在C++ 專案中呼叫python程式將svm模型匯入並進行實時預測, 並將預測結果傳回C++專案













