2015-06-21 56 views
1

我想在python 2.7中使用Bigfloat庫。Bigfloat - 錯誤的精度

from bigfloat import * 

f1 = Context(precision=2000) 

with precision(2000): f1 = 1e-19*1e-19*9e9/((1-1e-18)*(1-1e-18))-1e-19*1e-19*9e9 

with precision(100): f2 = 1.6e-27*1.6e-27*6.6e-11/(1e-18*1e-18) 

print BigFloat(f1) print f2 

Python給我f1=0,但事實並非如此。我用g ++測試了它,結果是1.75e-46

這是我的程序中的錯誤嗎?用Bigfloat計算精度是不可能的?它在lib中是錯誤的嗎?

+4

您使用的是正常的浮標,而不是由bigfloat庫實現的浮標。 – interjay

+0

我該怎麼辦?我沒有找到一個用BigFloat創建變量的例子。 – user84055

+0

您需要在進行計算之前創建BigFloat實例,而不是之後。 '1e-19 * 1e-19'是兩個普通浮標的乘法,而不是大浮標。我沒有使用這個庫,所以我不知道確切的用法。 – interjay

回答

1

舉例來說,您可以使用bigfloat庫來計算f1的精度爲256位。

>>> from bigfloat import BigFloat, precision 
>>> with precision(256): 
...  x = BigFloat('1e-19') 
...  y = BigFloat('9e9') 
...  z = BigFloat('1e-18') 
...  f1 = x * x * y/((1 - z) * (1 - z)) - x * x * y 
... 
>>> f1 
BigFloat.exact('1.800000000000000002700000000000000003600000000000000004500006811997284879750608e-46', precision=256) 

注使用BigFloat('1e-19'),其在當前的精度(256位)創建所述最接近的二進制浮子10**-19。這與BigFloat(1e-19)(沒有單引號)不同,因爲1e-19是Python浮點數,因此已經四捨五入爲53位精度。

查看documentation瞭解更多詳情。

然而,有了一點創造力和代數,在這裏你根本不需要高精度的庫。你可以重寫表達式f1爲:

f1 = x * x * y * (1/((1 - z) * (1 - z)) - 1) 

,並通過把一切都放到了一個共同點,括號中的量可以改寫爲(2 - z) * z/((1 - z) * (1 - z))。所以,你同樣可以計算f1爲:

f1 = x * x * y * (2-z) * z/((1 - z) * (1 - z)) 

並以這種形式,你不會失去精度時z非常小。所以,現在常規的Python花車都夠用:

>>> x = 1e-19 
>>> y = 9e9 
>>> z = 1e-18 
>>> f1 = x * x * y * (2 - z) * z/((1 - z) * (1 - z)) 
>>> f1 
1.8e-46 

如果你決定要使用高精度的浮點庫,我也建議看gmpy2庫。它基於與bigfloat相同的底層MPFR庫,但它的維護更好。