黑马程序员技术交流社区

标题: 关于浮点运算的一点分享 [打印本页]

作者: lingdu    时间: 2015-4-26 13:07
标题: 关于浮点运算的一点分享
JAVA的浮点运算
1、一道简单的计算题


class Test
{
    public static void main(String[] args)
    {
        System.out.println(0.05+0.01);
        System.out.println(1.0-0.42);
        System.out.println(4.015*100);
        System.out.println(123.3/100);
    }
}打印出的结果是:

0.060000000000000005
0.5800000000000001
401.49999999999994
1.2329999999999999

为什么会是这样的数值?再看一个代码


class Test1
{
    public static void main(String[] args)
    {
        System.out.printf("%1.20f\n",0.05f);
        System.out.printf("%1.20f\n",0.01f);
        System.out.printf("%1.20f\n",1.0f);
        System.out.printf("%1.20f\n",0.42f);
        System.out.printf("%1.20f\n",123.3f);
    }
}看上面的代码运行的结果:

0.05000000074505806000
0.00999999977648258200
1.00000000000000000000
0.41999998688697815000
123.30000305175781000000

这是float在计算机上面的表示的。

java中的float和double,采用IEEE754标准,实际上是用利用科学计数法来表达实数。即用一个尾数(Mantissa也叫有效数字 ),一个基数(Base),一个指数(Exponent)以及
一个表示正负的符号来表达实数。实数表示分为三个域。
float用32bit存储,double用64bit存储。
第一个域为符号域,0 表示数值为正数,而 1 则表示负数;
第二个域为指数域,对应于我们之前介绍的二进制科学计数法中的指数部分。其中单精度数为 8 位,双精度数为 11 位。float单精度的指数范围为-127 和 127 之间。
第三个域为尾数域,其中单精度数为 23 位长,双精度数为 52 位长。
造成无法准确的计算出来我们想要的结果,原因是科学计算法无法准确的存储,只有相近的取近似值

所以我们对于精确的计算采用的是BigDecimal类可以解决上面的问题。


作者: 崔小可    时间: 2015-4-26 13:19
很好  顶一个  
作者: 段立志    时间: 2015-4-26 13:44
66666666666
作者: 怪学究    时间: 2015-4-26 15:11
嗯嗯,受教了
作者: 澂澂    时间: 2015-4-26 16:02
一直弄不明白,现在有点明白了。
作者: xfliyy    时间: 2015-4-26 17:04
学习了......
作者: 893269222    时间: 2015-4-26 21:52
知道这么回事,没大看懂
作者: 不二情-昊    时间: 2015-4-26 22:09
受益匪浅啊
作者: 张乐    时间: 2015-4-26 22:23
感谢楼主分享!很长姿势哦!
作者: 邓熊财    时间: 2015-4-26 22:35
感觉很强大!!!
作者: frankzheng329    时间: 2015-4-27 00:23
感谢分享




欢迎光临 黑马程序员技术交流社区 (http://bbs.itheima.com/) 黑马程序员IT技术论坛 X3.2