内存对齐原则
- 1.结构(struct)(或联合(union))的数据成员,第一个数据成员放在offset为0的地方,以后每个数据成员存储的起始位置要,从该成员的大小或成员的子成员大小(数组、结构体)的整数倍开始(如int为4字节,则要从4的整数倍地址开始存储)
- 2.结构体作为成员:如果一个结构里有某些结构体成员,则结构体成员要从其内部 最大元素 大小的整数倍地址开始存储.(struct b,b里有char(1字节),int(4字节) ,double(8字节)等元素,那b应该从8的整数倍开始存储.)
- 3.收尾工作: 结构体的总大小,也就是sizeof的结果,.必须是其内部最大
成员的整数倍.不足的要补⻬
- 类的底层是结构体,类中的属性对象内存优化会使用到《二进制重排》。
- 内存排布遵循min算法。
二进制重排:是将内存中具有相同功能的内存空间,提出来重新放入新的内存中,提高代码的执行效率。
例1:
struct LGStruct1 {
char a; // 1 字节 占0的位置
//根据min算法和内存对齐原则 排布
double b; // 8 字节,1 ~7都不是8 的倍数,第8位是8的倍数,占位为 8~15
int c; // 4字节,第16的位置是4的倍数,占位为16~19
short d; // 2字节,第20的位置是2的倍数,占位为20~21
// 最后,根据对齐原则第3条,内存大小必须是最大内存的整数倍 ,所以为 24
} MyStruct1;
NSLog(@"%lu",sizeof(MyStruct1));
例2:
struct LGStruct2 {
double b; // 8字节 占位为 0~7
//根据min算法和内存对齐原则 排布
char a; // 1字节 第8的位置是1的倍数,占8的位置
int c; // 4字节 第9~11的位置不是4的倍数,第12的位置是4的倍数,占位为12~15
short d; // 2字节 第16的位置是2的倍数,占位为16~17
// 最后,根据对齐原则第3条,内存大小必须是最大内存的整数倍 ,所以为 24
} MyStruct2;
例4:
struct LGStruct3 {
double b; // 8字节 占位为 0~7
int c; //4字节 第8的位置是4的倍数,占位为8~11
char a; // 1字节 第12的位置是2的倍数,占位为12
short d; // 2字节 第13的位置不是2的倍数,第14的位置是2的倍数,占位为14~15
// 最后,根据对齐原则第3条,内存大小必须是最大内存的整数倍 ,所以为16
} MyStruct3;
总结:
- 第一个数据成员放在offset为0的地方,
*第二个之后的成员,根据当前成员的倍数进行补齐。
*最后,根据结构体大小 必须是其内部最大成员的整数倍进行补⻬。
网友评论