文章目录
一、浮点类型
1.1 浮点数
浮点数的本质是数学中的小数。
如,123.45
可以写成 12.345*10^1
,也可以写成1.2345*10^2
,小数点可以移动,所以叫浮点数。
1.2 浮点类型
1.2.1 字面浮点数
浮点数有两种表示方法,一种是直接写出来的小数,如123.45
;另一种是使用 E来表示,如1E10
表示的是1.0*10^10
。
1.2.2 浮点数类型
float
: 单精度浮点型(4 byte)
double
:双精度浮点型(8 byte)
long double
:多精度浮点型(8 byte)
二、浮点型的存储
2.1 二进制的权重
可以看到,二进制整数部分的权重是,1
、2
、4
…;小数部分的权重是,0.5
,0.25
,0.125
…
示例:
注意: 有些数字,如3.14
的小数部分 0.14
在转为二进制时,因为小数权重的原因,可能永远没法碰巧凑为0.14
,那就会不断通过1
、0
来尽可能的接近,所以后面可能会有很多位。
2.2 浮点数格式
根据国际标准 IEEE754,任意一个二进制浮点数都可以表示成一种固定格式:
(-1)^S
:表示符号位,当 S = 0,V是正数,当 S = 1时,V为负数。M
:表示有效数字,M >= 1 并且 M< 2。2^E
:表示指数位。
例如:
因为任意一个二进制浮点数都可以表示成上述形式,所以存储一个浮点数,只要存S,M,E
就行。
三、存储时的内存分布
3.1 S M E 所占的存储空间
3.2 S
当V是正数时,S = 0
当V是负数时, S = 1
3.3 M
因为 1<=M<2
,所以 M 可以写成 1.xxxxxx
的形式,在计算机保存 M
时,会默认这个数的第一位总是1
,因此可以被舍去,只保存后面的.xxxxxx
部分。
这样做的目的,是节省1位有效数字,多一位来放小数部分,精度会提高。
3.4 E
3.4.1 内存中存储的 E 的值
E为一个无符号整数(unsigned int
),把 8/11
个比特位中存储的数据当成一个无符号数看待,这意味着E
的范围不可能为负数。
- 如果E为
11
位,它的取值范围为0~2047
如果E为8
位,它的取值范围为0~255
但科学计数法中的E
是会出现负数的,如:
所以,为了解决这个问题,IEEE 754规定,存入内存时E
的真实值必须再加上一个中间数。
- 对于
8
位的E,这个中间数127
- 对于
11
位的E,这个中间数是1023
无论 E
的正负,都要加中间数,只是这种操作是为负数的 E
设定的,但既然设计了那就正负统一操作,便于管理。
3.4.2 从内存中取出的 E
3.4.2.1 E不全为0或不全为1
指数E的计算值减去127
(或1023
),得到真实值,再取出 M
后+1
,得到真实的浮点数。
3.4.2.2 E全为0
是加上中间数后存了0
,所以真实值应该是-127
(或 -1023
),E 是 -127
,此时数字已经相当小了,无限接近于0
。
规定:
- E的真实值为(1-127)/(1-1023)
- 有效数字
M
不再加上第一位的1
,而是还原为0.xxxxxx
的小数。这样做是为了表示±0
,以及接近于0
的很小的值。
3.4.2.3 E全为1
加上中间数后是全1
,即255
,那的真实值应该是 128
,此时数字是相当大的。
如果有效数字M
全为0
,表示±无穷大
(正负取决于符号位s
)。
3.5 示例
本文到此就结束啦,如果有帮助到您,希望可以得到您的一个赞!(如有哪里有错漏,望您指点!)