再谈字节对齐

来源:互联网 发布:tslint.json 编辑:程序博客网 时间:2024/04/29 06:36
再谈字节对齐
2009-05-01 21:32
请牢记以下3条原则:(在没有#pragma pack宏的情况下)

 

1:数据成员对齐规则:结构(struct)(或联合(union))的数据成员,第一个数据成员放在offset为0的地方,以后每个数据成员存储的起始位置要从该成员大小的整数倍开始(比如int在32位机为4字节,则要从4的整数倍地址开始存储。

 

2:结构体作为成员:如果一个结构里有某些结构体成员,则结构体成员要从其内部最大元素大小的整数倍地址开始存储.(struct a里存有struct b,b里有char,int ,double等元素,那b应该从8的整数倍开始存储.)

 

3:收尾工作:结构体的总大小,也就是sizeof的结果,.必须是其内部最大成员的整数倍.不足的要补齐.

 

 

等你看完此3条原则,2分钟已经过去,抓紧时间,实战3分钟:

 

 

typedef struct bb
{
int id;             //[0]....[3]
double weight;      //[7].....[15]      原则1
float height;      //[16]..[19],总长要为8的整数倍,补齐[20]...[23]     原则3
}BB;

typedef struct aa
{
char name[2];     //[0],[1]
int id;         //[4]...[7]          原则1

double score;     //[8]....[15]    
short grade;    //[16],[17]        
BB b;             //[24]......[47]          原则2
}AA;

int main()
{
AA a;
cout<<sizeof(a)<<" "<<sizeof(BB)<<endl;
return 0;
}

 

结果是

48 24
ok,上面的全看明白了,内存对齐基本过关.

 

再讲讲#pragma pack().

在代码前加一句#pragma pack(1),你会很高兴的发现,上面的代码输出为

32 16
bb是4+8+4=16,aa是2+4+8+2+16=32;

这不是理想中的没有内存对齐的世界吗.没错,#pragma pack(1),告诉编译器,所有的对齐都按照1的整数倍对齐,换句话说就是没有对齐规则.

 

明白了不?

 

那#pragma pack(2)的结果又是多少呢?对不起,5分钟到了,自己去测试吧.

原创粉丝点击