热门标签 | HotTags
当前位置:  开发笔记 > 编程语言 > 正文

js加减乘除精确计算

Javascript精确计算时的bug JS无法进行精确计算的bug 在做CRM,二代审核需求审核详情页面时。需要按比例(后端传类似0.8的小数)把用户输入的数字显示在不同的地方。

Javascript精确计算时的bug 


JS无法进行精确计算的bug 

在做CRM,二代审核需求审核详情页面时。需要按比例(后端传类似0.8的小数)把用户输入的数字显示在不同的地方。 
在做dubheInvest = invest * (1 - ratio);运算时发现问题。具体如下: 
示例代码: 

console.log( 1 - 0.8 );  //输出 0.19999999999999996 
console.log( 6 * 0.7 );  //输出 4.199999999999999 
console.log( 0.1 + 0.2 );  //输出 0.30000000000000004 
console.log( 0.1 + 0.7 );  //输出 0.7999999999999999 
console.log( 1.2 / 0.2 );  //输出 5.999999999999999 
通过上面举出的例子可以看到,原生的js运算结果不一定准确,会丢失精度。 
解决方案 

解决方案的原理是,将浮点数乘以(扩大)10的n次方倍,把浮点数变为整数后再进行相应的运算,最后将得到的结果除以(缩小)10的n次方倍。 
原理示例: 

将   console.log(1-0.8);  变为 console.log((1 * 10 - 0.8 * 10) / 10); 即可得到正确的值 
根据上述原理,可以封装一些方法出来解决此类问题。如下所示(Math.pow(x, y);表示求x的y次方): 

//加    
function floatAdd(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 floatSub(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);    
}    
       
//乘    
function floatMul(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 floatDiv(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){}     
        
      r1=Number(arg1.toString().replace(".",""));  
   
      r2=Number(arg2.toString().replace(".",""));     
      return (r1/r2)*Math.pow(10,t2-t1);     
}  

  


推荐阅读
  • 1、创建高级对象使用构造函数来创建对象构造函数是一个函数,调用它来例示并初始化特殊类型的对象。可以使用new关键字来调用一个构造函数。下面给出了使用构造函数的新示例。 ... [详细]
  • 开发笔记:js正则表达式属性及方法的使用
    篇首语:本文由编程笔记#小编为大家整理,主要介绍了js正则表达式属性及方法的使用相关的知识,希望对你有一定的参考价值。正则表达式直接量 ... [详细]
  • JS加密解密
    leta=汪政..222RRRp767868^*%^*%344h哈哈;letb=udp.d(ud(a));//需要加密的内容letc=udp. ... [详细]
  • 微信小程序官方组件展示之表单组件input源码
    以下将展示微信小程序之表单组件input源码官方组件能力,组件样式仅供参考,开发者可根据自身需求定义组件样式,具体属性参数详见小程序开发文档。功能描述:输入框。该组件是原生组件, ... [详细]
  • PNG在IE6下透明问题的解决办法
    2019独角兽企业重金招聘Python工程师标准做Web开发的朋友一定都知道PNG是一个相当不错的图片格式,但是这个好的格式却在IE6时代造成了麻烦࿰ ... [详细]
  • 前端微服务二
    为了解决庞大的一整块后端服务带来的变更与扩展方面的限制,出现了微服务架构(Microservices):微服务是面向服务架构(SOA)的一种变体,把应用程序设计成一系列松耦合的细粒 ... [详细]
  • 最近想用js做一个简单的计算器,不过网上的例子好像大部分都是直接从左到右挨个计算,就好像1+2*5,就会先计算1+2,再计算3*5,并没有实现运算符的优先级,这里找到了一种方法实现,来总结一下。不过这 ... [详细]
  • 看下面的代码:window.onload=someFunction;很多时候我看到使用这种代码,甚至我使用相同的代码.但是, ... [详细]
  • 编程语言是从哪蹦出来的——大型伦理寻根现场
    Hello,我是Alex007,一个热爱计算机编程和硬件设计的小白,为啥是007呢?因为叫Alex的人太多了,再加上每天007的生活,Alex007就诞生了。聊一聊编程到底是啥,怎 ... [详细]
  • JS动态生成表格案例 ... [详细]
  • 开发笔记:Python之父重回决策层
    篇首语:本文由编程笔记#小编为大家整理,主要介绍了Python之父重回决策层相关的知识,希望对你有一定的参考价值。在GuidovanRossum(吉多· ... [详细]
  • 篇首语:本文由编程笔记#小编为大家整理,主要介绍了展会&NBSP如果值空相关的知识,希望对你有一定的参考价值。 ... [详细]
  • 上次我们总结了React代码构建后的webpack模块组织关系,今天来介绍一下Babel编译JSX生成目标代码的一些规则,并且写一个简单的解析器,模拟整个生成的过程。我们还是拿最简 ... [详细]
  • 开发笔记:携程2019校招编程题
    本文由编程笔记#小编为大家整理,主要介绍了携程2019校招编程题相关的知识,希望对你有一定的参考价值。携程今年的机试题为20道选择+3编程由于今天最后提交时第三题 ... [详细]
  • 詮釋為何一切的參數通報的都是值,不可能經由歷程援用通報參數“值”的寄義這裏的值,指的是,複製傳進來的對象的地點,把這個複製值賦給參數援用通報的寄義直接將變量自身的地點傳進去,直接把 ... [详细]
author-avatar
洛特大人_382
这个家伙很懒,什么也没留下!
PHP1.CN | 中国最专业的PHP中文社区 | DevBox开发工具箱 | json解析格式化 |PHP资讯 | PHP教程 | 数据库技术 | 服务器技术 | 前端开发技术 | PHP框架 | 开发工具 | 在线工具
Copyright © 1998 - 2020 PHP1.CN. All Rights Reserved | 京公网安备 11010802041100号 | 京ICP备19059560号-4 | PHP1.CN 第一PHP社区 版权所有