关于JS浮点精度问题

在JS中 0.1 + 0.2 = 0.30000000000000004 而不是0.3

console.log((0.1).toString(2))  ====>0.0001100110011001100110011001100110011001100110011001101

console.log((1).toString(2))  ====>  1


这是因为js中的浮点数使用IEEE 754标准的双精度浮点数表示


IEEE双精度格式具有53位有效数字精度(包含符号号),并总共占用64位。

双精度二进制小数,使用64个比特存储。

1位
11位
52位
S(符号位),编号63
E(阶码位),编号62 ~52
M(小数位),编号51 ~ 0
0表示正,1表示负
−1022~+1023加上1023
任意

最高位63位是符号位,1表示该数为负,0表示该数为正;
    62-52
位,一共11位是指数位;
    51-0
位,一共52位是尾数位。


十进制0.1 

=> 二进制0.00011001100110011…(循环0011)  ====>    0.1  相当于 1/16+1/32+ 1/256 +1/512  ............

=>尾数为1.10011001100110011001100(共52位,除了小数点左边的1),指数为-4(二进制移码为00000000100),符号位为0  

=> 计算机存储为:0 00000000100 1001100110011001111001 

=> 因为尾数最多52位,所以实际存储的值为0.00011001100110011001100110011001100110011001100110011001 

而十进制0.2 

=> 二进制0.0011001100110011…(循环0011)  

=>尾数为1.10011001100110011001100(共52位,除了小数点左边的1),指数为-3(二进制移码为00000000011),符号位为0 

=> 存储为:0 00000000011 1001100110011001111001  

因为尾数最多52位,所以实际存储的值为0.00110011001100110011001100110011001100110011001100110011 

 那么两者相加得:     

    0.00011001100110011001100110011001100110011001100110011001 

+  0.00110011001100110011001100110011001100110011001100110011 (确认??)  

=  0.01001100110011001100110011001100110011001100110011001100 

转换成10进制之后得到:0.30000000000000004 

解决方法

1    可以奖浮点数化为整数   0.1+0.2 =1+2/10   ; 相当于( a*10+b*10)/10


关于浮点数

浮点数格式使用科学计数法表示实数。科学计数法把数字表示为系数(coefficient)(也称为尾数(mantissa)),和指数 (exponent)两部分。
比如 3.684*10^2. 在十进制中,指数的基数为 10,并且表示小数点移动多少位以生成系数。每次小数点向前移动时,指数就递增;
每次小数点向后移动时,指数就递减。例如,25.92 可表示为 2.592 * 10^1,其中 2.592 是系数,值 10^1 是指数。必须把系数和指数相乘,才能得到原始的实数。
另外,如 0.00172 可表示为 1.72*10^-3,数字 1.72 必须和 10^-3 相乘才能获得原始值。
 计算机系统使用二进制浮点数,这种格式使用二进制科学计数法的格式表示数值。数字按照二进制格式表示,那么系数和指数都是基于二进制的,而不是十进制,
例如 1.0101*2^2
在十进制里,像 0.159 这样的值,表示的是 0 + (1/10) + (5/100) + (9/1000)。
相同的原则也适用二进制。比如,1.0101 乘以 2^2 后,生成二进制值 101.01 ,这个值表示二进制整数 5,加上分数 (0/2) + (1/4) 。
这生成十进制值 5.25 。下表列出几个二进制小数以及它们对应的十进制值:


  • 0
    点赞
  • 0
    收藏
    觉得还不错? 一键收藏
  • 0
    评论
评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值