int i = Integer.MAX_VALUE;//2147483647 float f = 2.1474836E9f;//单步跟踪下, f 的值是 2.14748365E9
int j = (int)f; boolean bi = i == j;
System.out.println("bi= "+bi);上面这段代码执行后,bi将等于 true,是什么原因呢? 单步跟踪下, f 的值是 2.14748365E9,明显与程序中不一样。搜索了一下,也没找到有关float 和double在java中存储的清楚详细的说明。谁有这个的详细说明?(最好画个图)
int j = (int)f; boolean bi = i == j;
System.out.println("bi= "+bi);上面这段代码执行后,bi将等于 true,是什么原因呢? 单步跟踪下, f 的值是 2.14748365E9,明显与程序中不一样。搜索了一下,也没找到有关float 和double在java中存储的清楚详细的说明。谁有这个的详细说明?(最好画个图)
解决方案 »
- a++ 与 ++a 区别
- java 打印输出乱,以及Ajax输出乱码问题
- 正则表达式如何提取两个字符串之间的字符串
- Xsocket 客户端运行一次后就会自己关闭
- 急求LADP认证
- java编译器有没有dll文件
- 求My eclipse和My sql,有的可以传给我或者提供下载也可,谢谢
- 问题啊~~~~~~~~谢谢帮我看看~~~:) 在线
- 请问子类能不能重构父类的构造方法,如果能,怎么做?
- 在Java中如何获得外部的环境变量
- 引入import sun.misc.BASE64Decoder和import sun.misc.BASE64Encoder的问题
- 急!如何用正则表达式提取字符串中如下内容?
这里不详细解释,LZ可查阅相关资料
有几个知识点:
1.计算机中浮点数的基数是2.
2.指数部分有偏移量(float为127, double为1023)
3.规格化的表示小数点左边一定为1.(二进制数)
4.float类型 符号位占1位,指数部分占8位,尾数占23位(因为规格化表示,小数点左边一定为1,所以实际有24位精度)
5.double类型 符号位占1位,指数部分占11位,尾数占52位(因为规格化表示,小数点左边一定为1,所以实际有53位精度)看一个例子float 0.6吧:
第一步,把十进制转2进制:
0.6的二进制表示(乘2取整,顺序表示):
.1001 1001 1001 1001 1001 1001 1001 ... 无限循环下去。第二步,计算尾数部分:
把.1001 1001 1001 1001 1001 1001 1001 ...规格化表示(小数点移到第一个非0书右边)就是:
1.001 1001 1001 1001 1001 1001 1001 ...,右移了1位。
由于规格化表示的数小数点左边一定为1,把这个1舍弃,并保留float尾数能表示的23位,最终尾数部分是:
001 1001 1001 1001 1001 1001第三步,计算指数部分:
由于计算尾数时右移了1位,相当于乘以2的负1次,所以指数为-1,加上float偏移量127,最后指数为126,
二进制表示为 0111 1110第四步,符号部分:
0.6为正数,符号位为0最终0.6在计算机中的表示就是: 符号位 指数 尾数
0 0111 1110 001 1001 1001 1001 1001 1001
--------------------------------------------------------------
我们再从这个2进制来计算10进制数:(2的指数次 * 尾数)
符号位0--> 为正
指数 0111 1110:为126, 减去偏移量127,结果为-1.
尾数 001 1001 1001 1001 1001 1001: 规格化的时候小数点左边人掉了一个1,现在加上:
1.001 1001 1001 1001 1001 1001,转为10进制就是:
1*2^0 + 1*2^-3 + 1*2^-4 + .....= 1.19999992847442626953125
1.19999992847442626953125 * 2^-1 = 0.599999964237213134765625
所以最终结果是一个无限接近于0.6而不能精确表示0.6
结贴,散分