浮点数的表示

浮点数

摘要

我们说的浮点数包括单精度浮点数和双精度浮点数,浮点数的实现、运算是按照IEEE 754标准进行的,IEEE 754标准是计算机上使用最为广泛的浮点标准。

浮点数的表示

浮点数分为两个组成部分:整数部分(i)和小数部分(f),通常,将浮点数表示为 ± i.f Xβe,其中i.f 称为有效数字,它的数字个数称为有效数字精度,β为基数,e为指数,±表示该浮点数的正负。当其中整数部分i符合:0i<β时,被称为“规格化数”,否则被称为“非规格化数”。

一个浮点数FIEEE 754标准中可以用F = (-1)s x M x 2e 的形式表示,说明如下:

(1)符号s决定浮点数是正数(s=0)还是负数(s=1)

(2)有效数字M是二进制小数,M满足1M20M1

(3)指数e2的幂,它的作用是对浮点数加权(就是指数的阶)。

一个规格化的32位浮点数Df的真值可表示为:Df = (-1)s x (1.M) x 2e  e = E -127

一个规格化的64位浮点数Df的真值为:Df = (-1)s x (1.M) x 2e  e = E -1023

浮点格式

浮点格式是一种数据结构,该结构规定了构成浮点数的各个部分在所属字节上的布局及编码,按照规定,这些字节被划分为3个部分:

(1)一个符号位s,编码符号s

(2)n位的偏置指数e(en1…e1e0 其中ei1或者0),编码为指数E

(3)k位的小数f(fk-1f1f0 其中fi 1或者0),编码为有效数字M

E的取值范围为0-255(无符号整数),实际数值为e=E-127E也可以被称为“移码”,而e则被称为“阶码”。

浮点数0.0(或者非常接近0.0的浮点数)的表示方法:e = 0(即en1…e1e0 全部为零),有效数字M = f = 0. fk-1f1f0,有效数字的前导有效位为0

±的表示方法:e 的位模式即en1…e1e0全部为1,小数M = f = 0,即f的位模式全部为零,当s = 1时,为+∞,当s = -1时,为-∞;

规格化数的表示:e 的位模式即en1…e1e0不全为1,也不全为零,小数部分fk-1f1f0不全为零,通过调整e来实现,使1M2,此时M = 1. fk-1f1f0,也就是说:有效数字的前导有效位总是1,因此该位不需显式给出,只需通过指数隐式给出。

单精度格式

C语言中,单精度浮点型变量存储为 IEEE 32 位,就是4个字节,它的范围在负数的时候是从 -3.402823E38 -1.401298E-45,而在正数的时候是从 1.401298E-45 3.402823E38。其浮点格式为:23位小数f8位指数e1位符号s。将这些字段连续存放在一个32位字里(4字节),并对其进行编码(高字节在后,低子节在前),其中第31位为符号位s,记为s31】;23:30位包含8位,为指数e,记为e23:30】;0:22位包含23位,为小数f,记为f0:22】;如图1所示。

双精度格式

按照IEEE-754标准来规定浮点数的存储格式,在C语言中,双精度浮点数用8字节存储,分为三个部分:符号位、阶和尾数。阶即指数,尾数即有效小数位数。符号位为1位,阶占11位,尾数占53位。编码规则为(也按照高字节在前,低字节在后顺序):

s63】,e53:62】,f0:52】。

单精度浮点数实例

对于内部存储数据(四字节:0011 1111  0110 0110  0110 0110  0110 011022表示二进制,10表示十进制):

    符号位:(最左侧)S=0。这表示是个正数

    指数:(左侧第2-9位)E=(01111110)2=(126)10,所以e=E-127=-1

    尾数:(最后的23位)M=(1100110 01100110 01100110)2m=(1.M)2 = (1.7999999523162841796875)10,或者m = (1.1100110 01100110 01100110)2

    该二进制小数转为10进制的计算方式为1 + (1/2+1/4) + (1/32+1/64) + (1/512+1/1024)……

实际值:N=1.7999999523162841796875*2-1 = 0.89999997615814208984375,这个数据是0.9的单精度浮点数的实际内部存储,从中可以看到计算机对实际浮点数的存储是有一定的误差的。或者在N = (1.1100110 01100110 01100110)2 * 2-1m值基础上进行移位操作,得到N = (0.11100110 01100110 01100110)2 = (0.89999997615814)10

二进制、十进制转换问题

十进制小数转换为二进制:小数乘以2取整,余下小数部分继续乘以2取整……,最后这些被取整数顺序排列,就是小数所要的二进制表示形式,例如对0.917,就有如下过程:

0.917  x  2  = 1.834  1

0.834  x  2  = 1.668  1

0.668  x  2  = 1.336  1

0.336  x  2  = 0.672  0

0.672  x  2  = 1.344  1

0.344  x  2  = 0.688  0

0.688  x  2  = 1.376  1

0.376  x  2  = 0.752  0

0.752  x  2  = 1.504  1

0.504  x  2  = 1.008  1

0.008  x  2  = 0.016  0

0.016  x  2  = 0.032  0

0.032  x  2  = 0.064  0

0.064  x  2  = 0.128  0

0.128  x  2  = 0.256  0

0.256  x  2  = 0.512  0

0.512  x  2  = 1.024  1

0.024  x  2  = 0.048  0

0.048  x  2  = 0.096  0

0.096  x  2  = 0.192  0

0.192  x  2  = 0.384  0

0.384  x  2  = 0.768  0

0.768  x  2  = 1.536  1

0.536  x  2  = 1.072  1

于是就有:(0.917)10  = (0.11101010  11000000  10000011)2 = (1.1101010 11000000  10000011)2 单精度,共24位,单精度存储为4字节,分布如下所示:高字节在前,低字节在后

  S0】,e01111110】,f1101010  11000000  10000011】,于是就是:

  0011 1111  0110 1010  1100 0000  1000 0011

二进制小数转换为十进制 f0/2 + f1/4 + f2/8 + … + fi/2i+1 + … + fi为对应二进制数位数字,为1或者0

于是对于单精度4字节二进制数:0011 1111  0110 1010  1100 0000  1000 0011,转换为10进制浮点数就是:

S0 = 0为正数;

E01111110 = (126 - 127)10 = -1;

F1101010  11000000  10000011】;m=(1.M)2 = (1.83399999)10,实际值为:1.83399999 ×2-1 = 0.91699999;跟0.917还是有些差别,这个差别称之为转换误差,显然误差和转换的精度有关。

 

评论 1
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

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

抵扣说明:

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

余额充值