C/C++数据边界对齐的注意事项

Nimat ·
更新时间:2024-11-10
· 722 次阅读

  有关C/C++数据边界对齐的基本知识我不再描述了,下面我根据我的一些经验简单描述一下数据边界对齐的注意事项。

  1、数据对齐的使用

  当初弄明白数据边界对齐的原理,并没有思考具体怎么使用,而是为了应付面试。

  当建立一个struct或者class,必须考虑其成员变量的数据对齐,来尽可能减少空间的浪费,把占用空间小的元素放在struct/class的前面。例子:

struct align {  double b;  char c;  int a; };

  以上这个结构体,由于 double b 排在前面,所以该结构体以double作为数据对齐的方式,double为8个字节的空间,则一下c与a也将会分别占用8个字节的空间,则:

sizeof(align)

  后则会占用3*8=24个字节的空间。再来看下面这个结构体:

struct align {  char c;  int a;  double b; };

  c排在前面,采用1字节对齐,接着到a,则采用4字节对齐,到此,align占用了8个字节:c:4个字节,a:4个字节。然后到b,double型采用8字节对齐,由于a+c的空间已经是8字节了,所以c+a+b所占用的空间可以等价于 4+4+8 = 16 个字节,直接比上一个结构体节省了8个字节。

  用法:把struct/class里的成员变量的大小排个序,按照从小到大的顺序写入结构体内,则能尽可能节省内存空间。

  特殊情况:

  有的class/struct内的成员变量具有上下文关系,我们可以把相关的成员存储在一起,以便于理解和维护,建议不按照上面的用法来节省内存空间。如:

struct product {  int cdrom_amount;  double cdrom_unit_price;  int phone_amount;  double phone_unit_price; };

  这个结构体,建议按照这种成员排列序列吧,别动手术了。

  2、强制数据对齐

  应该知道 #pragma pack(2) 的使用:

#pragma pack(2) struct align {  char c;  int  a;  double b; }; #pragma pack()

  以上这个结构体强制采用2对齐的方式,则该结构体占用的空间为 2+4+8 = 14 。对某个结构体使用强制数据对齐之后,注意恢复数据对齐的方式,即在结构体的后记得加上:

#pragma pack()

  还有要注意的是不要滥用这个功能,可能会破坏内存的堆栈,或者强制转化的时候发生一些不可预料的情况。慎用。

  以上是我总结的,由于表达能力有些欠缺,可能也有我一些理解错误或者理解不透彻的地方,希望大家能指出,望本文能抛砖引玉。



c+ 数据 边界 C++

需要 登录 后方可回复, 如果你还没有账号请 注册新账号