欢迎来到“Under The Hood”第四期。上期我们讨论了JVM的字节码指令集,本期我们继续这个话题。本文我们来看看JVM中的浮点运算。
JVM支持IEEE-754浮点数标准(1985)。该标准定义了32位和64位浮点数的格式,以及在此之上的各种运算。在JVM中,浮点运算是基于32位float数和64位double数的。对每个操作float数的字节码,都有一个对应的操作double数的版本。
浮点数由4部分组成:数符(sign),尾数(mantissa),基数(radix)和阶码(exponent)。数符取1或-1。尾数是一个正数,它持有浮点数的有效位。阶码是尾数和符号位应该乘以的基数的正(负)幂数。这4个部分用下面的公式得到浮点数的值:
sign * mantissa * radixexponent |
浮点数有很多种表现形式,因为你总是可以把浮点数的尾数乘以基数的某次幂,然后通过改变阶码的方式获得原先的值。例如,-5可以写成如下以10为基数的形式:
Sign | Mantissa | Radix | Exponent |
-1 | 50 | 10 | -1 |
-1 | 5 | 10 | 0 |
-1 | 0.5 | 10 | 1 |
-1 | 0.05 | 10 | 2 |
每个浮点数都有一个规范化的表示形式。如果浮点数的尾数符合下面的公式,我们就说这个浮点数是规范化的。
1/radix <= mantissa < 1 |
规范化的以10为基数的浮点数,尾数的小数点出现在第一个非0的有效位前面。-5的规范化形式是-1*0.5*10 1。也就是说,规范化的浮点数中,小数点的左边是0,右边第一位不是0。其他不是这种形式的浮点数都是非规范化数。注意,0没有规范化的形式,因为它没有非0数放在小数点后面。数字0们总是感叹“为什么要规范化我们呢?”。
JVM中的浮点数以2为基数,所以JVM中的浮点数值用下面的公式获得:
sign * mantissa * 2exponent |
JVM中的浮点数的尾数用2进制数表示。规范化的二进制数小数点出现在非0最高有效位前面。由于二进制数系统只有2个数字,1和0,所以最高有效位上的数字总是1。
float和double数的最高有效位是它的符号位,float的最后23位是尾数位,而double则为最后52位。阶码处在符号位和尾数中间,float为8位,double为11位。float的完整2进制形式如下,s表示符号位,e表示阶码,m表示尾数。
s eeeeeeee mmmmmmmmmmmmmmmmmmmmmmm |
正数的符号位为0,负数的符号位为1。尾数总是一个正的二进制数,但不是二进制补码数。如果符号位为1,浮点数的值是负的,但尾数仍然是正的。
阶码有3种解释方式。如果阶码位全是1,意味着这是一个特殊的浮点数,表示正无穷或负无穷,或者不是一个数(NaN)。NaN是特定运算的结果,比如除法的除数是0。阶码的所有位为0,表示这是一个非规范化的浮点数。除上面2种情况之外的阶码,都是规范化浮点数的一部分。
尾数部分其实隐式包含了一个额外的精度位。float数的尾数占23位,却有24个精度位;同一样的,double数的尾数占52位,却有53个精度位。因为尾数部分的最高有效位是可以被预测的,所以并没有包含在尾数中。JVM中,浮点数的阶码可以指明该数是不是一个规范化浮点数。如果阶码位全0,则为非规范化数,且最高有效位肯定是0。其他情况下,则为规范化浮点数,且最高有效位肯定是1。
在JVM中,任何浮点运算都不会抛出异常。类似除数为0的问题操作,JVM会返回一些特殊值,比如正/负无穷,或NaN。尾数位全是0的情况下,如果阶码位全是1,符号位是0,则表示正无穷;如果阶码位全是1,符号位是1,则表示负无穷。如果阶码位全是1,尾数位不全是0,则表示NaN。JVM总是为NaN使用相同的尾数:最高有效位是1,其他全为0。下表列出了上面提到的3中特殊值:
Special float values | Float bits (sign exponent mantissa) |
+Infinity | 0 11111111 00000000000000000000000 |
-Infinity | 1 11111111 00000000000000000000000 |
NaN | 1 11111111 10000000000000000000000 |
非全0和非全1的阶码表示规范化尾数要乘以的2的幂数。可以把阶码当做一个正数,然后减去一个偏移量,这样就能得到实际的幂数。对float数来说,偏移量是126;而double数,则为1023。例如,一个float数的阶码为00000001,则幂数为-125(1 – 126),这是float中最小的幂数。再看一个例子,如果阶码是11111110,则幂数为128(254 – 126),这是float中最大的幂数。下表列出了一些正规化的浮点数:
Normalized float values | Float bits (sign exponent mantissa) | Unbiased exponent |
Largest positive (finite) float | 0 11111110 11111111111111111111111 | 128 |
Largest negative (finite) float | 1 11111110 11111111111111111111111 | 128 |
Smallest normalized float | 1 00000001 00000000000000000000000 | -125 |
Pi | 0 10000000 10010010000111111011011 | 2 |
阶码位全0,说明尾数没有规范化,也隐含说明了最高有效为是0,而不是1。这种情况下,幂数为浮点数的最小幂数。对float来说,是-125。这意味着,规范化尾数乘以2 -125的浮点数,它的阶码为00000001,而非规范化尾数乘以2 -125的浮点数,它的阶码为00000000。阶码范围底端的非规范化数修正值,使得下溢出较为平缓。如果最小阶码用来表示规范化数,下溢成0的最小数值会更大一些。 换句话说,让最小阶码表示非规范化数,可以使浮点数能表示更小的数值。虽然非规范化数的精度没有规范化数高,但是,这相对于阶码一旦达到最小规范化数值,浮点数就会下溢成0来说,非规范化数更好一些。
Denormalized float values | Float bits (sign exponent mantissa) |
Smallest positive (non-zero) float | 0 00000000 00000000000000000000001 |
Smallest negative (non-zero) float | 1 00000000 00000000000000000000001 |
Largest denormalized float | 1 00000000 11111111111111111111111 |
Positive zero | 0 00000000 00000000000000000000000 |
Negative zero | 1 00000000 00000000000000000000000 |
相关推荐
JVM指令码表,JVM运行原理学习的必备工具。常量入栈指令、局部变量值转载到栈中指令、将栈顶值保存到局部变量中指令、wide指令、通用(无类型)栈操作指令、类型转换指令、整数运算、浮点运算等指令。
jvm源码
jvm 配置jvm参数 配置jvm参数
jvm源码,jvm-native的源码,jvm支行机制,可对jvm的运行过程进行分析 个人网站:https://www.zhangjunbk.com
JVM图解-JVM指令-JVM原型图.rar
深入解析jvm深入解析jvm深入解析jvm深入解析jvm深入解析jvm深入解析jvm
46页PPT详解JVM,46页PPT详解JVM,46页PPT详解JVM,46页PPT详解JVM,46页PPT详解JVM,46页PPT详解JVM,46页PPT详解JVM,46页PPT详解JVM,46页PPT详解JVM,46页PPT详解JVM,46页PPT详解JVM,46页PPT详解JVM,46页PPT...
主要是JVM内存分配及简单的JVM性能调优
学习关于JVM基础,java内模型的全面透析,Jar hell问题以及解决办法,Class文件格式 • Java编译执行流程 • ClassFile的格式介绍 • ClassFile中FieldInfo和MethodInfo介绍 • 类型描述Descriptor介绍 • ClassFile...
本系列课程从JVM基础到高级实战,老师手把手教你如何进行JVM调优,思路清晰,没有废话,旨在挑战高薪。 课程亮点: 1、基于阿里arthas进行JVM调优; 2、基于代码排查OOM问题,拒绝空讲; 3、总结JVM通用的调优思路;...
jvm
JVM面试资料。 JVM结构:类加载器,执行引擎,本地方法接口,本地内存结构; 四大垃圾回收算法:复制算法、标记-清除算法、标记-整理算法、分代收集算法 七大垃圾回收器:Serial、Serial Old、ParNew、CMS、Parallel...
首先讲述JVM的基本概念和原理、架构等。最后一HelloApp讲述JVM的工作过程
jvm 详细介绍,了解jvm各个组成部分和功能
JVM配置资料JVM配置资料JVM配置资料JVM配置资料
Introduction to JVM Languages English | 2017 | ISBN-10: 178712794X | 390 pages | PDF/MOBI/EPUB (conv) | 6.42 Mb Key Features This guide provides in-depth coverage of the Java Virtual Machine and its ...
Jvm入门,Jvm入门,Jvm入门,Jvm入门,Jvm入门,Jvm入门
讲JVM工作原理、垃圾回收讲的非常好的一个ppt
JVM原理讲解和调优 JVM原理讲解和调优 JVM原理讲解和调优
JVM指令主要分为:本地变量表到操作数栈类指令、操作数栈到本地变量表类指令、常数到操作数栈类指令、将数组指定索引的数组推送至操作数栈类指令、将操作数栈数存储到数组指定索引类指令、操作数栈其他相关类指令、...