1、区别struct与union
(1)设有以下说明和定义:(假定在32位机器上)
typedef union
{
long i;
int k[5];
char c;
} DATE;
struct data
{
int cat;
DATE cow;
double dog;
} too;
DATE max;
求语句 printf("%d", sizeof(struct data)+sizeof(max));的执行结果是:
答:DATE是一个union, 变量公用空间. 里面最大的变量类型是int[5], 占用20个字节. 所以它的大小是20. data是一个struct, 每个变量分开占用空间. 依次为int4 + DATE20 + double8 = 32. 所以结果是 20 + 32 = 52.
2、理解运用大小端格式:
==============================
大端模式,是指数据的高字节保存在内存的低地址中,而数据的低字节保存在内存的高地址中,这样的存储模式有点儿类似于把数据当作字符串顺序处理:地址由小向大增加,而数据从高位往低位放;这和我们的阅读习惯一致。
小端模式,是指数据的高字节保存在内存的高地址中,而数据的低字节保存在内存的低地址中,这种存储模式将地址的高低和数据位权有效地结合起来,高地址部分权值高,低地址部分权值低。
=== === === === === === === === ===
(2)请写一个C函数,若处理器是Big_endian的,则返回0;若是Little_endian的,则返回1。
解答:
int checkCPU()
{
union w
{
int a;
char b;
} c;
c.a = 1;
return (c.b == 1);
}
剖析:
采用Little-endian模式的CPU对操作数的存放方式是从低字节到高字节,而Big-endian模式对操作数的存放方式是从高字节到低字节。
例如,16bit宽的数0x1234在Little- endian模式CPU内存中的存放方式(假设从地址0x4000开始存放)为:
内存地址 存放内容
0x4000 0x34
0x4001 0x12
而在Big-endian模式CPU内存中的存放方式则为:
内存地址 存放内容
0x4000 0x12
0x4001 0x34
32bit宽的数0x12345678在Little-endian模式CPU内存中的存放方式(假设从地址0x4000开始存放)为:
内存地址 存放内容
0x4000 0x78
0x4001 0x56
0x4002 0x34
0x4003 0x12
而在Big-endian模式CPU内存中的存放方式则为:
内存地址 存放内容
0x4000 0x12
0x4001 0x34
0x4002 0x56
0x4003 0x78
联合体union的存放顺序是所有成员都从低地址开始存放,利用该特性可以轻松地获得CPU对内存采用Little-endian还是Big-endian模式读写。
0x4000 0x4001 0x4002 0x4003
c.b=0x1
c.a=0x1 0x0 0x0 0x0 小端
=== ===
c.b=0x1 //一个字节也要先从低地址开始存
c.a=0x0 0x0 0x0 0x1 大端