首頁  >  文章  >  web前端  >  如何解決js浮點數精度問題

如何解決js浮點數精度問題

一个新手
一个新手原創
2017-09-25 10:34:061598瀏覽

大多數語言在處理浮點數的時候都會遇到精確度問題,但在JS裡似乎特別嚴重,來看一個例子

alert(45.6*13);
結果居然是592.800000000001,當然加法之類的也會有這個問題
那這是js的錯誤嗎?
當然不是,你的電腦做著正確的二進制浮點運算,但問題是你輸入的是十進制的數,電腦以二進制運算,這兩者並不是總是轉化那麼好的,有時會得到正確的結果,但有時候就不那麼幸運了
alert(0.7+0.1);//輸出0.7999999999999999
alert(0.6+0.2);//輸出0.8

#你輸入兩個下兩個十進制數,轉換為二進制運算過後再轉換回來,在轉換過程中自然會有損失了
但一般的損失往往在乘除運算中比較多,而JS在簡單的加減法裡也會出現這類問題,你也看到了,這個誤差也是非常小的,但是卻是不該出現的
那該怎麼解決呢,ECMA4似乎給了解決方法,但是現在倒不是那麼實用的
一種方法,例如0.7+0.1,先把0.1和0.7都乘10,加完之後再除10
另外可以自己寫點函數來解決這個問題,自己百度谷歌一下應該有很多,但是最好還是不要用JS做一些複雜的浮點運算,畢竟JS更多的作用不在於此

<script type="text/javascript">  

    // 两个浮点数求和  
    function accAdd(num1,num2){  
       var r1,r2,m;  
       try{  
           r1 = num1.toString().split(&#39;.&#39;)[1].length;  
       }catch(e){  
           r1 = 0;  
       }  
       try{  
           r2=num2.toString().split(".")[1].length;  
       }catch(e){  
           r2=0;  
       }  
       m=Math.pow(10,Math.max(r1,r2));  
       // return (num1*m+num2*m)/m;  
       return Math.round(num1*m+num2*m)/m;  
    }  

    // 两个浮点数相减  
    function accSub(num1,num2){  
       var r1,r2,m;  
       try{  
           r1 = num1.toString().split(&#39;.&#39;)[1].length;  
       }catch(e){  
           r1 = 0;  
       }  
       try{  
           r2=num2.toString().split(".")[1].length;  
       }catch(e){  
           r2=0;  
       }  
       m=Math.pow(10,Math.max(r1,r2));  
       n=(r1>=r2)?r1:r2;  
       return (Math.round(num1*m-num2*m)/m).toFixed(n);  
    }  
    // 两数相除  
    function accp(num1,num2){  
       var t1,t2,r1,r2;  
       try{  
           t1 = num1.toString().split(&#39;.&#39;)[1].length;  
       }catch(e){  
           t1 = 0;  
       }  
       try{  
           t2=num2.toString().split(".")[1].length;  
       }catch(e){  
           t2=0;  
       }  
       r1=Number(num1.toString().replace(".",""));  
       r2=Number(num2.toString().replace(".",""));  
       return (r1/r2)*Math.pow(10,t2-t1);  
    }  

    function accMul(num1,num2){  
       var m=0,s1=num1.toString(),s2=num2.toString();   
    try{m+=s1.split(".")[1].length}catch(e){};  
    try{m+=s2.split(".")[1].length}catch(e){};  
    return Number(s1.replace(".",""))*Number(s2.replace(".",""))/Math.pow(10,m);  
    }  

  </script>  

    <script>  
    document.write("使用js原生态方法");  
    document.write("<br/> 1.01 + 1.02 ="+(1.01 + 1.02));  
    document.write("<br/> 1.01 - 1.02 ="+(1.01 - 1.02));  
    document.write("<br/> 0.000001 / 0.0001 ="+(0.000001 / 0.0001));  
    document.write("<br/> 0.012345 * 0.000001 ="+(0.012345 * 0.000001));  
    document.write("<br/><hr/>");  
    document.write("<br/>使用自定义方法");  
    document.write("<br/> 1.01 + 1.02 ="+accAdd(1.01,1.02));  
    document.write("<br/> 1.01 - 1.02 ="+accSub(1.01,1.02));  
    document.write("<br/> 0.000001 / 0.0001 ="+accp(0.000001,0.0001));  
    document.write("<br/> 0.012345 * 0.000001 ="+accMul(0.012345,0.000001));  
    </script>
#

以上是如何解決js浮點數精度問題的詳細內容。更多資訊請關注PHP中文網其他相關文章!

陳述:
本文內容由網友自願投稿,版權歸原作者所有。本站不承擔相應的法律責任。如發現涉嫌抄襲或侵權的內容,請聯絡admin@php.cn