大端存储和小端存储是两种不同的字节序排列方式,用于表示多字节数据类型在内存中的存储方式。在计算机中,多字节数据类型通常由多个字节组成,如 16 位整数、32 位浮点数等。每个字节都有一个唯一的地址,计算机在存储多字节数据类型时,需要考虑字节的排列顺序。
(1)大端存储
也称为网络字节序,是指在内存中高位字节存放在低位地址,低位地址存放在高位地址。也就是说,最高位的字节存储在最低的地址上,而最低位的字节存储在最高的地址上。
(2)小端存储
也称主机字节序,是指在内存中低位字节存放在低位地址,高位字节存放在高位地址。也就是说,最低位的字节存储在最低的地址上,而最高位的字节存储在最高位的地址上。
例如,变量 x 的类型为 int(占据四个字节大小),值为 19088743,它的十六进制表示为 0x01234567。则 x 从高到低的位可表示为,高字节为 0x01,低字节为 0x67。假设 x 的地址为 0x100,则 x 将被存储在 0x100~0x103 的地址范围。
若采用大端存储,示意图为:
若采用小端存储,示意图为:
注意:同类型的机器之间进行数据传递时,必须考虑数据的存储方式。TCP/IP 协议规定在网络上进行数据传递时采用大端存储。
分不清高地址、低地址、高位、低位的看这里
(3)怎么判断大端存储和小端存储
可以利用结构体来判断系统的字节序,其基本原理是利用结构体的对齐规则来判断不同字节序下结构体的大小和成员变量的内存地址。
在大端存储中,结构体的第一个成员变量的地址和整个结构体的地址相同;在小端存储中,结构体的最后一个成员变量的地址和整个结构体的地址相同。
以下是一个使用结构体来判断字节序的实例代码:
#include<iostream>
#include<stdlib.h>
using namespace std;
struct Test
{
char c;
int i;
};
int main()
{
struct Test test = { 'A',0x12345678 };
char* p = (char*)&test;
if (*p == 'A')
{
printf("这是大端存储\n");
}
else if (*p == 0x78)
{
printf("这是小端存储\n");
}
else
{
printf("无法判断\n");
}
return 0;
}
在上面代码中,我们定义了一个结构体 Test,其中包含了一个字符类型的成员变量和一个整型类型的成员变量。我们给字符类型成员变量赋值为‘A’,给整型类型成员变量赋值为‘0x12345678’。然后,我们将结构体的地址转换为 char 类型的指针,判断第一个字节的值,如果是字符‘A’。则说明系统采用的是大端存储;如果是 0x78,则说明系统采用的是小端存储。
需要注意的是,结构体对其规则可能因编译器和编译选项而异,因此在使用结构体来判断字节序时需要特别小心,最好使用特定的类型定义和编译选项来确保对其规则的一致性。