结构体的字节对齐

在用sizeof运算符求算某结构体所占空间时,并不是简单地将结构体中所有元素各自占的空间相加,这里涉及到内存字节对齐的问题。

1) 结构体变量的首地址能够被其最宽基本类型成员的大小所整除;

2) 结构体每个成员相对结构体首地址的偏移量都是成员大小的整数倍;

3) 结构体的总大小为结构体最宽基本类型成员大小的整数倍。 

类型 int short long char bool float double 指针 枚举
字节 4 2 4 1 1 4 8 4 4

下面看一下sizeof在计算结构体大小的时候具体是怎样计算的:

1.test1   空结构体


typedef struct node
{
     
}S;

则sizeof(S)=1。

2.test2

typedef struct node1

{

    int a;

    char b;

    short c;

}S1;

则sizeof(S1)=8。(int)4+(char)1+(填充)1+(short)2=8,且能被(成员最宽类型)4整除。

4.test4  含有静态数据成员 

typedef struct node3

{

    int a;

    short b;

    static int c;

}S3;

则sizeof(S3)=8。(int)4+(short)2=6+(填充)2=8,能被(成员最宽类型)4整除。

这里结构体中包含静态数据成员,而静态数据成员的存放位置与结构体实例的存储地址无关(注意只有在C++中结构体中才能含有静态数据成员,而C中结构体中是不允许含有静态数据成员的)。

5.test5  结构体中含有结构体

typedef struct node4

{

    bool a;

    S1 s1;

    short b;

}S4;

则sizeof(S4)=16。(bool)1+(填充3)+(S1)8+(short)2=14+(填充)2=16,能被(成员最大宽度S1的宽度)4整除。

S1占8字节,而S1中最长数据类型为int,占4个字节。

6.test6

若在程序中使用了#pragma pack(n)命令强制以n字节对齐时,默认情况下n为8。则比较n和结构体中最长数据类型所占的字节大小,取两者中小的一个作为对齐标准。

如果在程序开头使用命令#pragma pack(4),对于下面的结构体

typedef struct node5

{

    bool a;

    S1 s1;

    double b;

    int c;

}S5;

则sizeof(S5)=24。因为强制以4字节对齐,而S5中最长数据类型为double,占8字节,因此以4字节对齐。在内存中存放方式为:

  |-----------a--------|   4字节

  |--------s1----------|   4字节

  |--------s1----------|   4字节

  |--------b-----------|   4字节

  |--------b-----------|   4字节

  |---------c----------|    4字节

猜你喜欢

转载自blog.csdn.net/mianjiao6806/article/details/85012345