很久之前就想将内存对齐这块儿知识点总结记录下来,无奈本人患有very very严重的拖拉症,直到今天才下决心将这件事儿解决掉,废话不多说了,开工!(ps:本人所用编译器version为 gcc Ubuntu4.9.2-10 ubuntu13 4.9.2)
结构体到底占多大的空间呢?先看一下下面这道题的输出结果:
#include<stdio.h>
typedef struct test
{
char a;
int b;
double c;
}TEST;
int main(void)
{
TEST test1;
printf("%ld\n",sizeof(test1));
return 0;
} 不妨大胆猜想,结构体所占空间是不是其成员所占空间的代数和呢??按照这个猜想,该题的答案应该为13,然而事实却让人大跌眼镜,本题输出的结果为16。google一下知这是因为计算机中存在一种叫做内存对齐的机制导致了该结果的发生。
在计算机中通常会让CPU从内存中一次读取若干个字节的数据,而不是一次只读取一个字节的数据,这样的好处是提高了计算机的效率,然而坏处也显而易见。
假设CPU一次从内存中读取四个字节的数据,而现在内存中存在一个char型的数据和一个int型的数据,如果内存不对齐,当CPU第一次跨越四个字节寻址找到了一个char型的数据,而此时CPU的指向到了int型的中间区域,导致这个int型变量未找到,然后CPU会返回去再次寻找,直到找到该int型变量。这样不但没能提高效率,反而增加了CPU的负担。因此我们通常会在第一个char型变量后边填充一部分数据来保证每次寻址时地址都是该数据的整数倍,这样就避免了上述“错误”的发生,也就是所谓的内存对齐。
内存对齐的规则很简单:
一、起始位置为成员数据类型所占内存的整数倍,若不足则不足部分用数据将内存填充为该数据类型的整数倍。
二、结构体所占总内存为其成员变量中所占空间最大数据类型的整数倍。
假设上题中结构体变量是从零号内存开始存储,则char型变量占一个字节,而后int型变量发现起始位置在一号内存处,并不满足起始位置为int型所占4字节整数倍的要求,故将一二三号内存填充满,从四号内存处开始存储该int型成员,当该int型成员存储完成后已经用了八个字节的空间,因此此时double型成员的起始位置为第八号内存,满足第一条条件,所以double型开始存储,存储完成后该结构体变量刚好占16个字节,刚好是最大数据类型double八个字节的整数倍,所以存储完成,因此该结构体变量占了16个字节。
原创声明:本文系作者授权腾讯云开发者社区发表,未经许可,不得转载。
如有侵权,请联系 cloudcommunity@tencent.com 删除。
原创声明:本文系作者授权腾讯云开发者社区发表,未经许可,不得转载。
如有侵权,请联系 cloudcommunity@tencent.com 删除。