C语言数据存储-浮点型

浮点型

浮点型的种类和表示范围

1、float:3.4E-38~3.4E38
2、double:1.7E-308~1.7E308
3、long double:3.4E-4932~1.1E4932

储存方式

二进制转化

我们以9.5为例,首先将一个浮点型数据转化为2进制形式,同时分为整数部分和小数部分
于是就有了1001.1
整数部分的转化与整型非常类似,然而小数部分非常有趣。
小数点后其实类比于十进制,第一位代表2^-1(即0.5)
第二位代表 2^-2(即0.25)…以此类推。所以9.5可以精确的表示有赖于0.5恰好可以表示为2的-1次方。
那我们来观察一下0.3=0.25(即2^-2)+
0.03125 (即2^-5)
+…
由此可知,不是所有小数都可以精确表示,所以浮点型数据的比较只能近似比较,直接比较两个浮点型==是没有意义的。

浮点数的储存 (IEEE 745)

我们以32位机器为例,同时还是取上文提到得9.5
在这里插入图片描述
(1)第一步,上文已经完成了9.5到2进制转化得到1001.1
(2)任何一个浮点数都可以写成(-1)^SM2*E(其中1≤M<2)
我们可以类比十进制中的科学计数法来理解此处得转化方法
M就类似于十进制中的有效数字,而E就代表指数,只不过此处转化为了2进制
(3)我们来解析上文中的S、E、M
S代表sign即符号位,S仅有一位,我们通过(-1)^S来表示正负
E代表exp即指数字,有8位,所以理论可代表的指数为0-255。但我们需要考虑到E可以取负数,所以E总是+127后存储(例如E为3,则实际存储为130,即表示为10000010;E为-3,则实际存储为124,即表示为01111100)
M为Fraction即有效数字,23位。因为我们约定1≤M<2,所以M的整数位一定为1,我们无需存储,只存其小数位即可
(4)故对于9.5 S为0,E为3,M为0011
对应二进制S 0
E 00000011
M 00110000000000000000000
综合起来就是00000001100110000000000000000000

一个实例

int main()
{
	int n = 9;
	//
	//0 00000000 00000000000000000001001
	//(-1)^0 * 0.00000000000000000001001 * 2^-126
	//
	float *pFloat = (float *)&n;
	printf("n的值为:%d\n", n);//9
	printf("*pFloat的值为:%f\n", *pFloat);//0.000000

	*pFloat = 9.0;
	//1001.0
	//(-1)^0 * 1.001*2^3
	//S=0
	//M=1.001
	//E=3     +127
	//01000001000100000000000000000000
	//
	printf("num的值为:%d\n", n);//直接打印整形时,就是2进制到十进制转换
	printf("*pFloat的值为:%f\n", *pFloat);//9.0
	return 0;
}

运行结果
在这里插入图片描述

关于E的一些注意点

(1)当E存储为00000000时,此时E实际值为-127,注意到2^-127是一个极小数,这时有效数字M不再补上1,我们认为它表示±0,或是无穷趋近于0的数字
(2)当E存储为11111111时,此时E实际值为128,注意到2^128是一个极大数,如果此时有效数字M全为0,则认为它趋近于±∞

  • 3
    点赞
  • 0
    收藏
    觉得还不错? 一键收藏
  • 4
    评论
评论 4
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

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

抵扣说明:

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

余额充值