眾所周知,c和c++中,經常用到的浮點數型別無論是float型別還是double型別都存在一定的精度與誤差,關於float與double所表示的範圍如下:
double的精度足夠日常使用,但是浮點數在計算機內部儲存的時候存在的誤差值是不可避免的,比如說數字5在計算機中儲存的資料根據運算方式的不同,結果可能是4.99999999998,也可能是5.0000000001,這在我們需要對浮點數進行一些特定的操作的時候,非常容易出現不必要的麻煩,比如我們需要對浮點數double n=3.8進行如下操作的時候:
取n的整數部分可以用:int a = int(n);
得到n的小數部分: double b = n - a;
對小數部分進行操作:b *= 10;
取b的整數部分可以用:int c = int(b);
對於以上操作,按照正確的邏輯,取3.8的整數部分3,再用3.8 - 3 = 0.8,然後0.8 * 10 = 8,取8的整數部分得8.但是程式的輸出結果顯然不想我們想象的那麼簡單:
int main()
return
0; }
對於以上**,如果輸入3.8,輸出結果為:
很顯然結果為7,下面新增幾句**來驗證一下:
很容易發現,第乙個ans取得是3.8的小數部分,結果是0.79999999999999982000,正確的結果顯然應該是0.8,但是由於浮點數在計算機中儲存的特性,計算機認為0.79999999999999982000就是0.8,顯然這給後續的運算已經產生了不必要的影響,那麼如何處理呢?下面來介紹eps的處理方法:
eps處理浮點數誤差的問題:
何為eps?
eps可以看成是epsilon的縮寫,可以用來表示乙個無窮小的量,通常取eps的值為:1e-10~1e-8 之間。
可以做什麼?
對於數字5,如果計算機儲存的資料為5.000000000000001,顯然對這種情況不需要用到eps進行補償,而對於有預設的類似於4.9999999999999998的資料,eps可以進行對它的預設值進行一定的補償,使其在計算機中的儲存值變成5.00000000000000或者5.000000000000001,這樣在後續的計算中就會解決因為儲存的誤差造成的不必要後果。下面同樣用**驗證一下:
#define eps 1e-10 //巨集定義eps為1e-10
int main()
return
0; }
輸出結果為:
結果一面了然。另外,對於負數的情況,只需要把ans + eps改為ans - eps即可,下面附上完整**:
#include
#include
#define eps 1e-10
using
namespace
std;
int main()
return
0;}
輸出結果:
總結:
double等浮點數比較問題,eps
在acm中,精度問題非常常見。其中計算幾何頭疼的地方一般在於 量大和精度問題,量問題只要平時注意積累模板一般就不成問題了。精度問題則不好說,有時候乙個精度問題就可能成為一道題的瓶頸,讓你debug半天都找不到錯誤出在哪。1.浮點數為啥會有精度問題 浮點數 以c c 為準 一般用的較多的是float,...
浮點數float累加誤差分析與解決
1.浮點數ieee 754表示方法 要搞清楚float累加為什麼會產生誤差,必須先大致理解float在機器裡怎麼儲存的,具體的表示參考 1 和 2 這裡只介紹一下組成 由上圖可知 摘在 2 浮點數由 符號位 指數字 尾數部分,三部分組成。由於機器中都是由二進位制儲存的,那麼乙個10進製的小數如何表示...
關於誤差分析以及浮點數的精度問題
浮點,簡單的講就是實數的意思。浮點數就是可以近似表示某個任意的實數。浮點精度分為 16位 一半 二進位制16 32位 單 binary32 十進位制32 64位 double binary64 decimal64 128位 四 binary128 decimal128 256位 八進位制 binar...