zoukankan      html  css  js  c++  java
  • float double 如何存储计算2 (这个写的也不错)

       目前java遵照IEEE制定的浮点数表示法来进行float,double运算。这种结构是一种科学计数法,用符号、指数和尾数来表示,底数定为2——即把一个浮点数表示为尾数乘以2的指数次方再添上符号。

            我们来看一段java代码:

    public class FloatToBinary {
    public static void main(String[] args) {
    float f1=8.5f;
    System.out.println("f1底层数据(十进制):"+Float.floatToIntBits(f1));
    int int1=Float.floatToIntBits(f1);
    System.out.println("f1底层数据(二进制):"+Integer.toBinaryString(int1));
    }
    }

    打印结果:
    f1底层数据(十进制):1091043328
    f1底层数据(二进制):1000001000010000000000000000000

    我们知道float与double分别在内存中占有32位和64位,见下:

      符号位  阶码 尾数 长度
    float 1 8 23 32
    double 1 11 52 64

    IEEE浮点数表示标准:

    V = (-1)s×M×2E

     E = e-Bias

    其中Bias表示偏移量,float的偏移量为Bias=2k-1-1=28-1-1=127,double的偏移量为Bias=210-1=1023

    浮点数在计算机中存储时,按照二进制科学计数法拆分为三个部分:符号位、指数部分和尾数部分。如下图所示:

    技术分享

    存储时,按照最高位存储符号位,次高位存储指数部分,低位存储尾数部分的次序存储。存储时的排列示意图如下:

    技术分享 技术分享

    float类型的内存分布如下图所示:

    技术分享

    double类型的内存分布如下图所示:

    技术分享

    编码规则

    在实际存储时要对使用二进制科学计数法表示的浮点数值的符号位、指数部分和尾数部分进行编码处理。一般需要分为规约形式的浮点数、非规约形式的浮点数和特殊值三种类型进行编码。其编码前后处理如下图所示:

    技术分享技术分享

    注:非规约浮点数主要用于扩大0值附近的浮点数表示范围,非规约浮点数的绝对值均小于规约浮点数的绝对值,即前者在实数轴上更靠近0,这样可以提高0附近的计算精度;一般C、C++中float和double的取值范围都是按照规约浮点数定义的,MSDN文档和相关教材也是这么说的,但部分编译器按照ANSI/IEEE Std 754-1985标准实现了非规约浮点数,本文末尾留有程序示例说明。

    符号位:0表示正数,1表示负数;

    指数部分: float的偏移量为2^8 - 1,double的偏移量为2^11 - 1;

    尾数部分:实际尾数部分中的小数点后的数值,规约浮点数使用标准的二进制科学计数法表示,其尾数范围在 [1,2),非规约浮点数的尾数部分范围在(0,1)。

    上面的理论在哪里都能看到,这只是IEEE754的定义而已,我们来实际用一下它是怎么表达小数的:

    ①求单精度8.5f 的二进制 过程。

    首先8.5是正数所以符号位为0;

    然后化为二进制,1*2^3+0*2^2+0*2^1+0*2^0 (整数部分)  . (小数点)   1*2^-1小数部分简化为1000.1

    要把二进制数变成(1.f)*2^(exponent)的形式,其中exponent是指数即1.0001*2^3.

    然后我们得到阶码为e=3+127=130 即阶码表示二进制为10000010.

    余下小数0001,我们补齐至23位即00010000000000000000000。

    这样符合结构 符号位   0   阶码 10000010 尾数00010000000000000000000

    然后我们来看一下8.5存储在内存中01000001000010000000000000000000  

    因为java.lang.Integer.toBinaryString() 方法返回一个字符串表示的整数参数,以2为底的无符号整数,所以在开始的程序打印结果我们添加一个0,与我们算出的结果就相同了。

    网上有很多关于float、double的转换解说,这里只是我涉及到了这块,然后自己去学习了一下,其实刚开始我看理论知识比较晕,后来看到别人以列子详细解说,然后再回头看理论,就发现也没那么难了。

    本文出自 “进击的程序猿” 博客,请务必保留此出处http://zangyanan.blog.51cto.com/11610700/1854836

    java基础之float、double底层运算

    标签:float   ieee754   double   

    原文地址:http://zangyanan.blog.51cto.com/11610700/1854836

  • 相关阅读:
    【黑金原创教程】【FPGA那些事儿-驱动篇I 】实验二十六:VGA模块
    mini2440 u-boot下设置tftp
    mini2440 u-boot禁止蜂鸣器
    【转载】帧缓冲驱动程序分析及其在BSP上的添加
    debian7 amd64版本添加对x86包的支持
    debian7配置
    u盘安装debian 7(Wheezy) stabe
    【python练习题】实现字符串反转
    【python练习题】 删除列表中的重复元素(list的应用)
    【python练习题】冒泡排序 和插入排序 (list的应用)
  • 原文地址:https://www.cnblogs.com/dzhou/p/9543118.html
Copyright © 2011-2022 走看看