数据在内存中的存储

1.整形在内存中的存储

整形在内存中存储的是二进制的补码。

存储方式分为大端字节序存储以及小端字节序存储。

大端字节序存储指的是高字节存储在低地址,低字节存储在高地址。

小端字节序存储指的是低字节存储在低地址,高字节存储在高地址。1.1为什么有大小端存储

因为在计算机系统中,都是以字节为单位的,都对应一个地址,那么对于大于一个字节位置安排的问题,就产生了大小端存储。

1.2如何用代码实现判断为什么存储

int pd()
{
	int i = 1;
	char b = *(char*)&i;
	//把i的第一个字节取出来,看是否为1.
	if (b == 1)
		return 1;
	else
		return 0;
}
int main()
{
	int ret = pd();
	if (ret == 1)
		printf("小端存储");
	else
		printf("大端存储");

	return 0;
}
1.3练习
int main()
{
	char a = -1;
	//char是有符号还是无符号,取决于编译器,大多数编译器底下是有符号的
	//-1的二进制为
	//100000000000000000000000000000001   -1的原码
	//111111111111111111111111111111110   -1的反码
	//111111111111111111111111111111111   -1的补码
	//-1是int类型的,把他存在char类型中,只剩下
	//11111111  -a
	// a打印是%d,又因为a是char类型的
	//所以高位补符号位,即
	//11111111111111111111111111111111  补码
	//10000000000000000000000000000000  反码
	//10000000000000000000000000000001  原码
	//即-1.
	signed char b = -1;
	unsigned char c = -1;
	//c与a前面相同,但c是无符号的,高位补0.
	//00000000000000000000000011111111
	//正数原反补相同。
	printf("a=%d,b=%d,c=%d", a, b, c);
	//%d打印的是有符号的整数,
	//%u打印的是无符号的
	return 0;
}
int main()
{
	char a = -128;
	//10000000000000000000000000010000000
	//11111111111111111111111111101111111
	//11111111111111111111111111110000000 -补
	//10000000 -a
	//11111111111111111111111111110000000
	//打印的是%u,是无符号型形,所以把这个当正数
	printf("%u", a);

	return 0;
}
int main()
{
	char a = 128;
	//00000000000000000000000000010000000 -原反补
	//10000000 -a
	// char是有符号的,高位补第1位
	//11111111111111111111111111110000000
	//打印的是%u,是无符号型形,所以把这个当正数
	printf("%u", a);

	return 0;
}
1.4 char在内存中的存储

即char是-128--127,unsigned char为0--255

1.5练习
int main()
{
    char a[1000] = { 0 };
    int i = 0;
    for (i = 0; i < 1000; i++)
    {
        a[i] = -1 - i;
        //观察上列圆圈,第1个数为-1,第二个为-2
        //所以逆时针一圈转回来之后,找到0.也就是255个数
    }
    printf("%d", strlen(a));
    //strlen找的是字符串长度,即\0之前的个数

    return 0;
}
int main()
{
	int a[4] = { 1,2,3,4 };
	int* ptr1 = (int*)(&a + 1);
	//&a取出的是整个数组的地址,加1跳过整个数组,即在4的后面
	// ptr1[-1]==*(ptr1-1).
	int* ptr2 = (int*)((int)a + 1);
	//把a的地址强转为数字,+1跳过一个字节
	// 假设a的地址为0x11,即17,+1变成0x12
	//01 00 00 00 02 00 00 00 03 00 00 00 04 00 00 00
	//a本来指向为01,加1往后了一个字节,int为4个字节
	// 所以*ptr2为 00 00 00 02
	//打印就是0x2000000(2前面的0无意义,无需打印)
	printf("%x,%x", ptr1[-1], *ptr2);
	return 0;
}

2.浮点数的存储

存的是S,M,E相关的值

M存的是小数点后面的数

E存的是加上一个中间值,8位的E,加127,11位的E,加1023

如何取出存储中的值

第一种(正常情况)

如何放进如何放出

第二种(E为全0)

此时E为1-127或1-1023,M前面也不加回1,而是为0.xxxxxx,无限趋向于+-0.

第三种(E为全1)

非常大,趋向于+-无穷

2.1 例题

int main()
{
	float f = 5.5f;
	//101.1
	//s=0
	//E=2
	//M=1.011
	//存的话先存s,到e,再到m
	//0 10000001 01100000000000000000000
	//0100 0000 1011 0000 0000 0000 0000 0000
	//每四个二进制=一个16进制
	//4 0 b 0 0 0 0 0
	//40 b0 00 00
	return 0;
}

2.2例题

int main()
{
	int n = 9;
	//0 00000000 00000000000000000001001
	//
	float* p = (float*)&n;
	//E为全0,打印为
	//0.00000000000000000001001*2^-126(次方)
	printf("%d", n);
	printf("%f", *p);
	//只能取得小数点后六位
	*p = 9.0;
	//1011.1
	//s=0;
	//E=3
	//M=1.0111
	//0 10000010 01110000000000000000000
	//所以n打印的就是这个
	printf("%d", n);
	printf("%f", *p);
	return 0;
}

评论 1
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

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

抵扣说明:

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

余额充值