在控制檯輸入0.1+0.2,會得出如下結果spa
即不等於0.3。下面咱們說一下緣由。3d
1、存儲原理code
1.在計算機中數字不管是定點數仍是浮點數都是以多位二進制的方式進行存儲的。
2.在JS中數字採用的IEEE 754的雙精度標準進行存儲(存儲一個數值所使用的二進制位數比較多,精度更準確)。對象
2、示例blog
在定點數中,若是咱們以8位二進制來存儲數字。
對於整數來講,十進制的35會被存儲爲: 00100011 其表明 2^5 + 2^1 + 2^0。
對於純小數來講,十進制的0.375會被存儲爲: 0.011 其表明 1/2^2 + 1/2^3 = 1/4 + 1/8 = 0.375
對於像0.1這樣的數值用二進制表示你就會發現沒法整除,最後算下來會是 0.000110011…因爲存儲空間有限,最後計算機會捨棄後面的數值,因此咱們最後就只能獲得一個近似值。
JS中採用的IEEE 754的雙精度標準也是同樣的道理在存儲空間有限的狀況下,當出現這種沒法整除的小數的時候就會取一個近似值,在js中若是這個近似值足夠近似,那麼js就會認爲他就是那個值。console
console.log(0.1000000000000001) // 0.1000000000000001 (中間14個0,會打印出自己) console.log(0.10000000000000001) // 0.1 (中間15個0,js會認爲兩個值足夠近似,因此輸出0.1)
因爲0.1轉換成二進制時是無限循環的,因此在計算機中0.1只能存儲成一個近似值。
另外說一句,除了那些能表示成 x/2^n 的數能夠被精確表示之外,其他小數都是以近似值得方式存在的。
在0.1 + 0.2這個式子中,0.1和0.2都是近似表示的,在他們相加的時候,兩個近似值進行了計算,致使最後獲得的值是0.30000000000000004,此時對於JS來講,其不夠近似於0.3,因而就出現了0.1 + 0.2 != 0.3 這個現象。固然,也並不是全部的近似值相加都得不到正確的結果。class
3、解決方法原理
方式一: 想辦法規避掉這類小數計算時的精度問題就行了,那麼最經常使用的方法就是將浮點數轉化成整數計算。由於整數都是能夠精確表示的。循環
0.1+0.2 => (0.1*10+0.2*10)/10
方式二 : js的Number對象有一個保留小數位數的方法:toFixed();傳入一個須要保留的位數就OK:二進制
(0.1+0.2).toFixed(10)==0.3
注:JS的小數點精確到第16位。