浮点数存储的规则讲解(例题讲解)

目录

一,提出问题

二,浮点数存储规则

二进制浮点数表示形式

IEEE 754规定

 IEEE 754特别规定

        指数E的特殊情况

  E全为0

  E全为1

三,解题思路


一,提出问题

    分析代码

#include<stdio.h>
int main()
{
	int n = 9;
	float* pFloat = (float*)&n;

	printf("n的值为:%d\n", n);
	printf("*pFloat的值为:%f\n", *pFloat);
	
	*pFloat = 9.0;
	printf("num的值为:%d\n", n);
	printf("n的值为:%F\n", *pFloat);

	return 0;
}

   运行结果:

为什么会得到这样的结果呢?

二,浮点数存储规则

 二进制浮点数表示形式

    (-1)^ S * M * 2 ^ E

    (-1)^ S 表示符号位 当S=0, V 为正数 S=1时候 V为负数

    M表示有效数字,大于等于1,小于2

    2^E表示指数为

例:

     十进制2.5, 写出二进制是 10.1 相当于 (-1) ^ 0 *1.01 * 2 ^ 1

     那么按照公式可以得到  S = 0   M = 1.01    E = 1

     十进制2.5, 写出二进制是 -10.1 相当于 (-1) ^ 1  * 1.01 * 2 ^ 1

      那么按照公式可以得到  S = 0   M = 1.01    E = 1

IEEE 754规定

IEEE(电气与电子工程师协会)https://baike.baidu.com/item/%E7%94%B5%E6%B0%94%E4%B8%8E%E7%94%B5%E5%AD%90%E5%B7%A5%E7%A8%8B%E5%B8%88%E5%8D%8F%E4%BC%9A/54975165?fromtitle=IEEE&fromid=150905&fr=aladdin

       对于32位浮点数(float单精度浮点类型类型) 最高的1位是符号位S 接下来的8位是指数E 剩下的23位为有效数字M

       对于64位浮点数(double双精度浮点类型类型) 最高的1位是符号位S 接下来的11位是指数E 剩下的52位为有效数字M

 IEEE 754特别规定

指数E的特殊情况

 首先,E为一个无符号整数( unsigned int)  这意味着,如果E 8 位,它的取值范围为 0~255 ;如果 E 11 位,它的取值范围为 0~2047 。但是,我们 知道,科学计数法中的E 是可以出 现负数的,所以IEEE 754 规定,存入内存时 E 的真实值必须再加上一个中间数,对于 8 位的 E ,这个中间数 是127 ;对于 11 位的 E ,这个中间数是1023 。比如, 2^10 E 10 ,所以保存成 32 位浮点数时,必须保存成 10+127=137,即 10001001。
 
       然后,指数E从内存中取出还可以再分成三种情况:
E不全为0或不全为 1  
    这时,浮点数就采用下面的规则表示,即指数 E 的计算值减去 127 (或 1023 ),得到真实值,再将 有效数字M 前加上第一位的 1

E全为0

这时,浮点数的指数 E 等于 1-127 (或者 1-1023 )即为真实值,
有效数字 M 不再加上第一位的 1 ,而是还原为 0.xxxxxx 的小数。这样做是为了表示 ±0 ,以及接近于
0 的很小的数字。

E全为1

这时,如果有效数字 M 全为 0 ,表示 ± 无穷大(正负取决于符号位 s

三,解题思路

   请看注释.....
int main()
{
	int n = 9;
	//00000000000000000000000000001001 - 9的补码
	//
	//0 00000000 00000000000000000001001
	//E = 1-127 = -126
	//M = 0.00000000000000000001001
	//(-1)^0 * 0.00000000000000000001001 * 2^-126
	//
	float* pFloat = (float*)&n;

	printf("n的值为:%d\n", n);//9
	printf("*pFloat的值为:%f\n", *pFloat);//0.0

	*pFloat = 9.0;//以浮点数的视角,存放浮点型的数字
	//1001.0
	//1.001 * 2^3
	//(-1)^0 * 1.001 * 2^3
	//S=0
	//E=3
	//M=1.001
	//0 10000010 00100000000000000000000
	//
	printf("num的值为:%d\n", n);//1,091,567,616
	printf("*pFloat的值为:%f\n", *pFloat);//9.0

	return 0;
}

       正是因为读取的方式不同才导致不同的结果!!!!

  • 1
    点赞
  • 1
    收藏
    觉得还不错? 一键收藏
  • 1
    评论

“相关推荐”对你有帮助么?

  • 非常没帮助
  • 没帮助
  • 一般
  • 有帮助
  • 非常有帮助
提交
评论 1
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

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

抵扣说明:

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

余额充值