今天在用VS写代码时发现相同的数字,用相同的打印方式打印出来的结果竟然不同。学习之下发现是不同数据在内存中存储方式不同所致

alt

首先,我们经常用到的类型有int类型、char类型。以char类型为例。

int main()
{
	char a = 'a';
	printf("%d\n", a);
	return 0;
}

上面这些代码输出的结果是97。经过我查阅ASCII码表字母'a'的对应数值后,我发现char类型是以得到字符对应的ASCII值转换成16进制数值的形式存入内存的。

再以int类型的9为例,它一共占了4个字节,32个比特位,所以它的二进制形式就是00000000000000000000000000001001

而浮点型的数字不同于int类型,它不仅有整数的位,它还有小数的位。那么它们是怎么在内存中存储的?

标准:根据IEEE754,任何一个二进制数字都可以表示为**(-1)^S* M * 2^E**。其中M表示有效数字1<=M<2,(-1)* S表示符号位。2^E表示指数位

eg:7.0可表示为(-1)^0* 01.11 * 2^2 。那么此时S=0,M=1.11,E=2

那么浮点数存储的重点就是关于S、M、E的存放,以常见的float和double类型为例,在32位操作平台下,float类型所占的空间是4个字节,而double类型所占的字节数是8。那么怎么去分配这些空间就是存储的关键。

alt

上面就是在float和double两个常见的类型中三个量存放的空间分配情况。既然分配好了空间,如何去将空间利用起来就是关键。

其中标准规定:

M:M既然是大于或等于1小于2,那么M肯定可以写成1.xxxx的形式,那么保存可以去掉前面的1,直接将后面的数字存起来就能提高精确度。

E:对于E,因为E在实际中可以是一个有符号的数字,所以在存放时,我们先給真实的值加上一个中间数就是它的存放值(32位时127,64位是1023)

那么以float b = 7.0为例:

当b = 7.0时,S=0,M=1.11,E=2。此时的空间布局是

alt

alt