python調用dll出現精度問題解決
問題:python 在調用dll 的時候出現瞭精度問題
總結:使用decimal庫進行轉換就可以正常傳遞。
遇到的問題具體情況
dll 生成函數代碼聲明如下
extern __declspec(dllexport) void LinearCompute(GoFloat64 currentX, GoFloat64 currentY, GoFloat64 targetX, GoFloat64 targetY, GoFloat64* resultX, GoFloat64* resultY);
使用python調用代碼
from ctypes import * # c_double 聲明c 雙精度小數變量 result_x = c_double(0) result_y = c_double(0) x_c = 1400. y_c = 1450. x_t = 1500. y_t = 5600. # byref 調用指針 dll.LinearCompute(c_double(x_c), c_double(y_c), c_double(x_t), c_double(y_t), byref(result_x), byref(result_y)) print(result_x.value, ' ', result_y.value)
但是輸出的內容顯示,輸入到函數中的 x_c ,y_c 等數據對不上。
這裡需要使用 decimal 庫進行精度方面轉換
所以以上代碼改為如下:
from ctypes import * from decimal import * result_x = c_double(0) result_y = c_double(0) x_c = Decimal(1400) y_c = Decimal(1450) x_t = Decimal(1500) y_t = Decimal(5600) dll.LinearCompute(c_double(x_c), c_double(y_c), c_double(x_t), c_double(y_t), byref(result_x), byref(result_y)) print(result_x.value, ' ', result_y.value)
然後運行的結果如下
可以看見 傳入的數值變得正常瞭。
附:https://www.jb51.net/article/275779.htm
Decimal類型的優點
Decimal類型是在浮點類型的基礎上設計的,但是它在幾個地方上要優於floating point:
- Decimal類型可以非常精確地在計算機中存儲,而學過c++的都知道,浮點型在計算機中是無法精確存儲的,比如1.1和2.2在計算機中存儲後,運算(1.1+2.2)表達式的值結果會是3.3000000000000003;Decimal類型則不會出現這種情況。同樣,由於無法精確存儲,浮點型也就無法精確計算(相對於Decimal類型),可以再測試(0.1+0.1+0.1-0.3)兩種類型的計算結果。
- Decimal類型會自動保留小數點後面不需要的0,以與輸入的精度相匹配,比如下面小程序中的例子:浮點型的1.20+1.30結果是2.5;而Decimal類型結果是2.50,這樣貌似比較人性化。
- Decimal類型可以根據需要自己設置小數點後精度。通過getcontext().prec = x (x為你想要的精度來設置,getcontext()函數下面再詳細介紹)。
- Decimal類型有很強的管理功能,它能夠根據需要設置,來控制輸出的格式,得到或者忽略某類錯誤(如除0,可以設置忽略它,而得到一個Infinity的Decimal值)。
比較重要的一點,如果使用 decimal 轉換小數時,需要使用 單引號 引起來。
from decimal import * print(Decimal(1.1) + Decimal(3.3)) print(Decimal(1.1) - Decimal(3.3)) print(Decimal(1.1) * Decimal(3.3)) print(Decimal(1.1) / Decimal(3.3)) #輸出結果 ''' 4.399999999999999911182158030 -2.199999999999999733546474090 3.630000000000000097699626167 0.3333333333333333781908292778 '''
但是如果使用字符串,就可以得到正常的結果瞭。
到此這篇關於python調用dll出現精度問題解決的文章就介紹到這瞭,更多相關python調用dll精度問題內容請搜索WalkonNet以前的文章或繼續瀏覽下面的相關文章希望大傢以後多多支持WalkonNet!