结构体相关知识2
作者:互联网
转接结构体相关知识1
4、结构体对齐(糅合第5点,默认的对齐大小)
(1)结构体对其规则:
(a)结构体变量的首地址一定 是这个结构体变量中最大的基础(内置)类型的大小的整数倍
(b)结构体变量中每一个成员 相对于结构体首地址的偏移 一定是该基础数据类型大小的整数倍
(c) 结构体变量的总大小 一定是这个结构体变量中最大的基础(内置)类型成大小的整数倍
对应结构体A来说,char a 是1个字节,占1个位,int b 是4个字节,而前面的所有变量一共占1个字节,1不能整除4,最少要+3个字节,所以int b前面必须有4个字节,此时加上int b就一共位8个字节,对char c来说,前面的变量一共占了8个字节,8可以整除1,所以前面不需要补字节,此时一共占9个字节,所有变量都放完之后,看总字节是否可以整除最大的基础类型的字节(此出最大的基础类型int ,字节位4),由于9不能整除4,所以最少加3,即最终结构体A占12个字节。
对应结构体B来说,int a 是4个字节,占4个位,char b 是1个字节,而前面的所有变量一共占4个字节,4能整除1,不需要补字节,此时加上char b就一共位5个字节,对char c来说,前面的变量一共占了5个字节,5可以整除1,所以前面不需要补字节,此时一共占6个字节,所有变量都放完之后,看总字节是否可以整除最大的基础类型的字节(此出最大的基础类型int ,字节位4),由于5不能整除4,所以最少加3,即最终结构体B占8个字节。
(2)默认内存大小:vs为8个字节,gcc为8个字节
如果允许修改的化,#pragma pack(2)//修改默认大小,2个字节2个字节的取
#pragma pack()//恢复默认大小
分析:用#pragma pack(2)//修改默认大小,对于结构体B来说,最大的基础类型的字节为2,int a,4个字节,double b为8个字节,4可以整除2(2为默认的最大基础类型字节大小),所以此时一共12个字节,char c为1个字节,12可以整除2,前面不需要补字节,此时一共13个字节,13不能整除最大的基础类型的字节(此出为2),所以+1个字节,最后一共14个字节。
(3)如何让设计一个结构体,既要满足规则又要尽可能小?
尽可能地将小的基础类型的变量放在前面
(4)如果不定义结构体变量,怎么计算结构体各个成员的相对开始变量的偏移量?
若可以定义结构体,用如下方法:
若不能定义结构体,
法1:
法2: 定义宏 #define MY_OFFSET(type,arg)((int)&(((type*)0)->arg))
代码:
//结构题对齐
struct Node
{
char a;
short b;
int c;
float d;
double e;
long long int f;
};
#define MY_OFFSET(type,arg)(((int)&((type*)0)->arg))
//求结构体中变量d的偏移
int main()
{
printf("%d\n", MY_OFFSET(Node, b));
printf("%d\n", MY_OFFSET(Node, c));
printf("%d\n", MY_OFFSET(Node, d));
printf("%d\n", MY_OFFSET(Node,e));
printf("%d\n", MY_OFFSET(Node, f));
}
结果:
标签:字节,int,知识,一共,相关,整除,变量,结构 来源: https://blog.csdn.net/li94263/article/details/121705260