震惊!计算机连0.3+0.6都算不对?浅谈IEEE754浮点数算数标准
>>> 0.3+0.6
0.8999999999999999
>>> 1-0.9
0.09999999999999998
>>> 0.1+0.1+0.1
0.30000000000000004
最初碰到这个问题是在写js的金额计算中遇到的,始终找不到是什么原因造成的,于是把锅甩给了JS:垃圾js浮点运算有bug!然后百度拷贝了一个解决浮点
运算的函数才解决了问题。
直到最近才发现,原来不仅js会“算不清”0.3+0.6,C#,JAVA,Python等很多语言都绕不过这个问题!
原来这是因为IEEE754浮点数算数标准,这个算数标准不使用小数点,而是使用分数和指数来表示小数,例如0.5会用1/2表示,0.75用1/2+1/4表示,0.875用1/2+1/4+1/8表示。然而有的小数无法使用有限的分数来表示,如0.1,使用1/16+1/32+1/256+1/512+...+1/8192+...表示,因此才造成了浮点数计算的误差。
怎么解决呢?C#,JAVA,Python都使用Decimal计算来替代浮点数的计算,尤其是涉及钱的计算!JS呢?百度一个处理函数调一下就ok啦~
这里附上js处理浮点预算的函数:
function add(a, b) {
var c, d, e;
try {
c = a.toString().split(".")[1].length;
} catch (f) {
c = 0;
}
try {
d = b.toString().split(".")[1].length;
} catch (f) {
d = 0;
}
return e = Math.pow(10, Math.max(c, d)), (mul(a, e) + mul(b, e)) / e;
}
function sub(a, b) {
var c, d, e;
try {
c = a.toString().split(".")[1].length;
} catch (f) {
c = 0;
}
try {
d = b.toString().split(".")[1].length;
} catch (f) {
d = 0;
}
return e = Math.pow(10, Math.max(c, d)), (mul(a, e) - mul(b, e)) / e;
}
function mul(a, b) {
var c = 0,
d = a.toString(),
e = b.toString();
try {
c += d.split(".")[1].length;
} catch (f) {}
try {
c += e.split(".")[1].length;
} catch (f) {}
return Number(d.replace(".", "")) * Number(e.replace(".", "")) / Math.pow(10, c);
}
function div(a, b) {
var c, d, e = 0,
f = 0;
try {
e = a.toString().split(".")[1].length;
} catch (g) {}
try {
f = b.toString().split(".")[1].length;
} catch (g) {}
return c = Number(a.toString().replace(".", "")), d = Number(b.toString().replace(".", "")), mul(c / d, Math.pow(10, f - e));
}
震惊!计算机连0.3+0.6都算不对?浅谈IEEE754浮点数算数标准的更多相关文章
- Ibatis 3.0 之前使用的都是2.0 3.0与2.0的内容有很大的不同
以前用过ibatis2,但是听说ibatis3有较大的性能提升,而且设计也更合理,他不兼容ibatis2.尽管ibatis3还是beta10的状态,但还是打算直接使用ibatis3.0, ibatis ...
- IntelliJ IDEA 项目文件旁边都有0%classes,0% lines covered
IntelliJ IDEA 项目文件旁边都有0%classes,0% lines covered,解决方法:http://yayihouse.com/yayishuwu/chapter/2247
- 网上的CSS例子编写都不太严谨,如*{ margin:0;padding:0;}
margin:0;padding:0; 一般情况下不可以用 *{margin:0;padding:0;} 来适配. 保证自己的严谨代码编写风格.
- 开源搜索 Iveely Search Engine 0.6.0 发布 -- 黎明前的娇嫩
快两年了,Iveely Search Engine已经走过了5个版本的岁月,虽出生“贫寒”,没有任何开源基金会的支持,没有优秀的“干爹.干妈”,它凭着它的爱好者的支持,0.6.0终于破壳而出,7年前, ...
- c语言‘\0’ ,‘0’, “0” ,0之间的区别
首先比较一下‘\0’和‘0’的区别.有一个共同点就是它们都是字符,在c语言中,字符是按其所对应的ASCII码来存储的,一个字符占一个字节.请翻开你的ASCII字符集表吧,一般在你的C语言教材的附录上, ...
- Iveely Search Engine 0.4.0 的发布
千呼万唤始出来,Iveely Search Engine 0.4.0 的发布 经过无数个夜晚的奋战,以及无数个夜晚的失眠,Iveely Search Engine 0.4.0 终于熬出来了,这其中 ...
- 如何解决JavaScript中0.1+0.2不等于0.3
console.log(0.1+0.2===0.3)// true or false?? 在正常的数学逻辑思维中,0.1+0.2=0.3这个逻辑是正确的,但是在JavaScript中0.1+0.2!= ...
- Ubuntu16.04安装cuda9.0+cudnn7.0
Ubuntu16.04安装cuda9.0+cudnn7.0 这篇记录拖了好久,估计是去年6月份就已经安装过几遍,然后一方面因为俺比较懒,一方面后面没有经常在自己电脑上跑算法,比较少装cuda和cudn ...
- 为什么js中0.1+0.2不等于0.3,怎样处理使之相等?(转载)
为什么js中0.1+0.2不等于0.3,怎样处理使之相等? console.log(0.1+0.2===0.3)// true or false?? 在正常的数学逻辑思维中,0.1+0.2=0.3这个 ...
随机推荐
- 聊聊Spring Cloud版本的那些事儿
说说Spring Cloud版本的那些事儿. 版本命名 之前提到过,Spring Cloud是一个拥有诸多子项目的大型综合项目,原则上其子项目也都维护着自己的发布版本号.那么每一个Spring Clo ...
- 安装mysql5.5.28的步骤 2017.6.27
http://blog.sina.com.cn/s/blog_7cd69a6501014x7h.html
- React官方文档笔记之快速入门
快速开始 JSFiddle 我们建议在 React 中使用 CommonJS 模块系统,比如 browserify 或 webpack. 要用 webpack 安装 React DOM 和构建你的包: ...
- opencron
opencron 是强大的管理linux crontab任务的系统,基于JAVA开发 http://github.com/wolfboys/opencron 一个功能完善真正通用的linux定时任务调 ...
- 【Unity游戏开发】Lua中的os.date和os.time函数
一.简介 最近马三在工作中经常使用到了lua 中的 os.date( ) 和 os.time( )函数,不过使用的时候都是不得其解,一般都是看项目里面怎么用,然后我就模仿写一下.今天正好稍微有点空闲时 ...
- Django中用户权限模块
Django中用户权限模块 1 auth模块 auth模块是Django提供的标准权限管理系统,可以提供用户身份认证, 用户组和权限管理. auth可以和admin模块配合使用, 快速建立网站的管理系 ...
- java创建线程的几种方式,了解一下
1.继承Thread,重写run() public class MyThread extends Thread{ @Override public void run() { System.out.p ...
- Android 应用加固(乐固)操作说明
此处引用腾讯云对加固的优点说明如下: 为什么应用需要加固? 若应用不做任何安全防护,极易被病毒植入.广告替换.支付渠道篡改.钓鱼.信息劫持等,严重侵害开发者的利益. 应用进行安全防护,防止应用分发后, ...
- MVC动态绑定下拉框
Controller: //获取下拉信息表 //_vendorsAppService.GetAllObj() 是获取下拉列表结果集 ViewData["vendlist"] = n ...
- 危险 AI 花名册
简评:臭不要脸 AI 名单,another side of AI. 这是一个可怕的 AI 清单,上面的各种商用 AI 项目都用于一些很恶劣的目的.请大家保持警惕. 区别对待类 · HireVue - ...