zoukankan      html  css  js  c++  java
  • js 浮点数计算Bug

    之前在写项目时候,直接对带小数点的数据进行运算,发现所得到的值并不是自己想要的。

    经过一系列学习后,发现在JavaScript中,浮点数运算都是先转换成二进制,在转成二进制的时候有出现无限循环小数,故之后的运算都出现了问题(这是基于IEEE754数值的浮点计算的通病)。

    因此,就翻阅了前公司的js工具库,找到一些用于运算的函数。

    // 加法
    function accAdd(arg1,arg2){   
      var r1,r2,m;   
      try{r1=arg1.toString().split(".")[1].length}catch(e){r1=0}   
      try{r2=arg2.toString().split(".")[1].length}catch(e){r2=0}   
      m=Math.pow(10,Math.max(r1,r2))   
      return ((arg1*m+arg2*m)/m).toFixed(2);   
    }
    // 除法
    function accDiv(arg1,arg2){
       var t1=0,t2=0,r1,r2;
       try{t1=arg1.toString().split(".")[1].length}catch(e){}
       try{t2=arg2.toString().split(".")[1].length}catch(e){}
       with(Math){
       r1=Number(arg1.toString().replace(".",""))
       r2=Number(arg2.toString().replace(".",""))
       return (r1/r2)*pow(10,t2-t1);
      }
    }
    // 乘法
    function accMul(arg1,arg2)
    {
       var m=0,s1=arg1.toString(),s2=arg2.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)
    }
    // 减法
    function accSubtr(arg1,arg2){
       var r1,r2,m,n;
       try{r1=arg1.toString().split(".")[1].length}catch(e){r1=0}
       try{r2=arg2.toString().split(".")[1].length}catch(e){r2=0}
       m=Math.pow(10,Math.max(r1,r2));
       //动态控制精度长度
       n=(r1>=r2)?r1:r2;
       return ((arg1*m-arg2*m)/m).toFixed(n);
    }
    

      找到这些工具函数,当有想加强这些函数的想法。比如当函数不只两个的时候。

    于是,在我的脑海就出现了两个念头,可实现其效果。

    1. 参数过多的时候,一遍一遍的递归自己(这个方法就不写了,反正就是递归)。

    2. 重构这个工具函数

    // 加法
    function accAdd() {
        let arr = Array.prototype.slice.call(arguments);
        let num = 0;
        arr.map(res => {
            let r1, r2, m;
            try { r1 = res.toString().split(".")[1].length } catch (e) { r1 = 0 };
            try { r2 = num.toString().split(".")[1].length } catch (e) { r2 = 0 };
            m = Math.pow(10, Math.max(r1, r2));
            num = (res * m + num * m) / m
        });
        return num;
    }

      

    // 减法
    function accSubtr() {
       let arr = Array.prototype.slice.call(arguments);
       let num = arr[0];
       arr.shift();
       arr.map(res => {
            let r1, r2, m, n;
            try { r1 = res.toString().split(".")[1].length } catch (e) { r1 = 0 };
            try { r2 = num.toString().split(".")[1].length } catch (e) { r2 = 0 };
            m = Math.pow(10, Math.max(r1, r2));
            n = (r1 >= r2) ? r1 : r2;
            num = ((num * m - res * m) / m).toFixed(n);
        }); 
        return num;  
    }
    

      

  • 相关阅读:
    ASP.NET Web API 控制器执行过程(一)
    ASP.NET Web API 控制器创建过程(二)
    ASP.NET Web API 控制器创建过程(一)
    ASP.NET Web API WebHost宿主环境中管道、路由
    ASP.NET Web API Selfhost宿主环境中管道、路由
    ASP.NET Web API 管道模型
    ASP.NET Web API 路由对象介绍
    ASP.NET Web API 开篇示例介绍
    ASP.NET MVC 视图(五)
    ASP.NET MVC 视图(四)
  • 原文地址:https://www.cnblogs.com/tzzf/p/9119309.html
Copyright © 2011-2022 走看看