• javascript 计算后结果失精度的问题解决


      

      近日,项目中遇到数值经过数学计算后出现失精度的问题,例如:0.35/10 = 0.034999999999999996。造成这一结果的原因就不再仔细分析了,太繁琐,时间紧也就没仔细去研究。直接说解决方案。

      解决方案也是来自网友的分享,大同小异,有扩展Number,给Number增加方法的,也有定义工具方法的。我采用的是扩展Number 的方式。代码如下:

     // 解决四维运算,js计算失去精度的问题
     //加法
     Number.prototype.add = function(arg){
          var r1,r2,m;
          try{r1=this.toString().split(".")[1].length}catch(e){r1=0}
          try{r2=arg.toString().split(".")[1].length}catch(e){r2=0}
          m=Math.pow(10,Math.max(r1,r2))
          return (this*m+arg*m)/m
     };
     //减法
     Number.prototype.sub = function (arg){
         return this.add(-arg);
     };
     //乘法
     Number.prototype.mul = function (arg){
         var m=0,s1=this.toString(),s2=arg.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) }; //除法 Number.prototype.div = function (arg){ var t1=0,t2=0,t3=0,r1,r2; try{t1=this.toString().split(".")[1].length}catch(e){} try{t2=arg.toString().split(".")[1].length}catch(e){} try{t3=arg.toString().split(".")[0].length}catch(e){} with(Math){ if(this > 1 && (t2 === 0 && arg === pow(10,t3-1))){ return this/arg; }else { r1=Number(this.toString().replace(".","")) r2=Number(arg.toString().replace(".","")) return (r1/r2).mul(pow(10,t2-t1)); } } };

      其中,网友分享出来的方法中除法原本只有 else 中的内容,但实际使用过程中发现在处理类似于 3.5/10 的时候仍会出现结果失精度的问题,所以擅自添加了个 if 判断。如有其他更好更全面的解决方式,请广大网友不吝留言告知。

      

      另,附上自定义函数的解决方式:

    //除法
    function accDiv(arg1, arg2) {
    
        var t1 = 0, t2 = 0, t3 = 0, r1, r2;
        try {
            t1 = arg1.toString().split(".")[1].length
        } catch (e) {
        }
        try {
            t2 = arg2.toString().split(".")[1].length
            t3 = arg2.toString().split(".")[0].length
        } catch (e) {
        }
        r1 = Number(arg1.toString().replace(".", ""))
        r2 = Number(arg2.toString().replace(".", ""))
        if (arg1 > 1 && (t2 === 0 && arg2 === Math.pow(10, t3 - 1))) {
            return arg1 / arg2;
        } else {
            r1 = Number(arg1.toString().replace(".", ""))
            r2 = Number(arg2.toString().replace(".", ""))
            return accMul((r1 / r2), Math.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 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
    }
    //减法
    function Subtr(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);
    }
  • 相关阅读:
    NHibernate中的Clear和Flush方法
    什么是POCO类
    node-vuecli 脚手架安装
    layui表单引入ueditor遇坑记
    PHP的九个超全局变量
    PHP的八个魔术常量
    PHP的七个数组指针函数
    TP6.0多应用模式隐藏路由中的应用名
    TP6.0中的密码验证逻辑、验证器的使用
    Vue 侦听器 watch
  • 原文地址:https://www.cnblogs.com/leo-lpf/p/9505657.html
Copyright © 2020-2023  润新知