字节对齐指的是定义一个变量(包括常量,以下出现的变量不再特别说明)时,该变量在计算机内存区域的起始地址按照多少的倍数来存放。比如按4对齐,则起始地址必须是4的倍数。字节对齐影响着计算机指令系统层读写变量的速度。这一点在计算机体系结构和汇编语言的书里面一般都有较详细的说明,在此不多作描述。主要总结一下编程时字节对齐的设置。
C++提供了指令来设置对齐方式。一个是pack pragma,该指令用来设置结构成员的对齐;另一个是align,用来设置整个类型的对齐。下面我们看一下这两个指令是如何影响变量在内存的存储的。
1、pack pragma
pack pragma设置了struct、union或class中各成员的对齐方式,结构成员对齐指的是成员相对于起始地址的偏移量。该指令基本用法如下:
#pragma pack(n)
它指定了结构成员按n(1,2,4,8,16)字节对齐,如果未指定n,则恢复成默认值。需要注意的是,它并不是指结构体中的每个成员都要按n对齐,而是按照每个成员的大小和n相比较小的值对齐。下面引用MSDN中C++ Preprocessor Reference部分关于pack指令的说明:
n (optional)
Specifies the value, in bytes, to be used for packing. The default value for n is 8. Valid values are 1, 2, 4, 8, and 16. The alignment of a member will be on a boundary that is either a multiple of n or a multiple of the size of the member, whichever is smaller.
即成员member的对齐值 align of member = min( pack setting value, sizeof(member) )
请看下面示例代码:
using namespace std;
#pragma pack(show) // 显示当前结构成员对齐设置
#pragma pack(8)
struct A
... {
int n;
char c;
short s;
} ;