一、为什么存在内存对齐
1.平台原因(移植原因): 不是所有的硬件平台都能访问任意地址上的任意数据的;某些硬件平台只能在某些地址处取某些特定类型的数据,否则抛出硬件异常。
2. 性能原因: 数据结构(尤其是栈)应该尽可能地在自然边界上对齐。 原因在于,为了访问未对齐的内存,处理器需要作两次内存访问;而对齐的内存访问仅需要一次访问。
总的来说结构体的内存对齐是拿空间来换取时间的做法。
二、结构体的内存对齐四规则
默认情况:默认的对齐值 8字节
1.基本数据类型有一个对齐值
2.自定义类型有一个对齐值 = 内部成员类型的最大值
3.程序的指定对齐值:#pragma pack(n) n == 2的幂次方 n可以等于2 4 8 16 …
4.程序的有效对齐值:程序的指定对齐值和数据类型对齐值得较小值
三、举例
例1
typedef struct Test //8
{
char a; //1 + 7
double b; //8
int c; //4 + 4
}Test;
void main()
{
Test t;
printf("Test size = %d", sizeof(Test));
}
分析:
char类型占一个字节,double类型占八个字节,int占四个字节;根据其对齐规则,内部成员类型的最大值为double(8个字节),所以char类型要补齐另外的七个字节,加上int的四个字节,一共是:1+7+8+4 = 20,此时20不是8的倍数,因此int要补四个字节。
结果:
例2
typedef struct Test //8
{
char a; //1 + 3
int c; //4
double b; //8
}Test;
void main()
{
Test t;
printf("Test size = %d", sizeof(Test));
}
分析同上
结果:
例3
typedef struct Test
{
short a; //2 + 6
struct
{
int b; //4 + 4
double c;//8
char d; //1 + 7
};
int e; //4 + 4
}Test;
void main()
{
Test t;
printf("Test size = %d", sizeof(Test));
}
结果:
例4 程序中有指定对齐值时
#pragma pack(2)
typedef struct Test
{
short a; //2
struct
{
int b; //4
double c;//8
char d; //1 + 1
};//14
int e; //4
}Test;
void main()
{
Test t;
printf("Test size = %d", sizeof(Test));
}
结果:
以上就是C语言程序中结构体的内存对齐详解的详细内容,更多关于C语言结构体内存对齐的资料请关注编程网其它相关文章!