C语言中,基本数据类型与操作系统有关(虽然直接与编译器相关),基本没有什么变化。比如在32位操作系统中,int占4个字节,long占4个字节,char占1个字节,double占8个字节。但是结构体的大小并不只与操作系统有关了,与编译器有比较大的关系。
不同的编译器有不同的对齐方式,下面以32为linux下gcc4.6为例,分析一下gcc中结构体对齐的问题。
C中可以使用#pragma pack(n)来手动设定对齐数值。gcc默认是4,即按照4字节对齐。一般有如下的对齐规则:
1、结构体的第一个数据成员的相对位置为0,后续数据成员按n指定的值和该数据成员自身大小中较小的那个进行对齐。
2、不仅需要数据成员对齐,结构体本身也需要对齐。按照n的值和结构体数据成员中最长的长度中较小的进行对齐。结构体本身对齐即结构体最终的大小须是对齐数值的倍数,且不小于所有数据成员对齐之后的和。
对齐也即意味着数据的相对地址开始值须是对齐数值的倍数。
struct test {
int i;//4
char c;//1
long l;//4
double d;//8
}
i占4字节,c占1字节,l占4字节,d占8字节,使用默认对齐数值4。按照第一条规则,对于i,4=n,按4对齐,则i占据[0,3];对于c,1<n,按1对齐,则c占据[4];对于l,4=n,按4对齐,则l占据[8-11];对于d,8>n,按n=4对齐,则d占据[12-19]。至此数据成员对齐完毕,占据了[0-19]共20个字节。
接着按照规则2进行结构体本身的对齐。结构体数据成员中最大的是d,占了8个字节,n默认为4,故按照最小值4进行对齐。12是4的倍数,且最接近数据成员大小之和。故此结构体最终的大小是20。
#pragma pack(n)中n的值之可能是1、2、4。可以用3试一下,编译器回报错。如果用8,编译器不会报错,但是按照规则计算的大小与实际的大小不一致,因为gcc又按照默认的4进行对齐了,可以测试一下,这里不再赘述。
n=1,n=2的情况与n=4的情况类似,按照规则对齐即可,略。
分享到:
相关推荐
该文档提供了详细解决结构体sizeof问题,从结构体内变量所占空间大小,默认内存对齐大小,强制内存对齐方法,变量在内存中布局的详细分析,语言言简意赅,绝无废话,为读者解决了大量寻找书籍的烦恼,读者可以花费几分钟的...
sizeof进行结构体大小的判断.sizeof进行结构体大小的判断.sizeof进行结构体大小的判断.
sizeof(结构体)和内存对齐 sizeof(结构体)和内存对齐 sizeof(结构体)和内存对齐 sizeof(结构体)和内存对齐
结构体数据成员指针对齐,通过指针偏移给数据成员赋值。
结构体的sizeof值,并不是简单的将其中各元素所占字节相加,而是要考虑到存储空间的字节对齐问题。这些问题在平时编程的时候也确实不怎么用到,但在一些笔试面试题目中出是常常出现,对sizeof我们将在另一篇文章中...
该文件详细介绍了用sizeof求取struct结构体内存大小的各种情况
结构体内存对其计算结构体大小,大神总结,很有用,结构体内存对其计算结构体大小,结构体内存对其计算结构体大小结构体内存对其计算结构体大小
关于结构体的内存对齐关于结构体的内存对齐关于结构体的内存对齐
结构体字节对齐规则,主要是介绍结构体字节对齐规则,内容有点长,但是很全面.
关于C语言中的结构体字节对齐问题,在《C与指针》一书中提到,但是似乎没有说清楚,还是我理解不完全?所以,根据书上和网上资料,总结一些关于C语言中的结构体字节对齐的知识。这里的讨论和代码,都在VS2010下,GCC...
这段时间移植公司的linux+i386程序到Arm+linux平台,本以为是件工作量很小的事情,以为只要改几个驱动程序就OK了,没想到在应用...其中最烦的事情就莫过于结构体内存边界对齐了。搞了这么久,终于终结了一些小经验。
C语言结构体的字节对齐及指定对齐方式.docx
首先看一下结构体对齐的三个概念值: 数据类型的默认对齐值(自身对齐): 1.基本数据类型:为指定平台上基本类型的长度。如在32位机器中,char对齐值为1,short为2,int,float为4,double为8; 结构体:其数据成员...
关于gcc编译结构体的对齐说明
数据结构 计算结构体大小
仔细分析,仔细琢磨,必有收获。
c++结构体简述(csdn)————程序
c/c++中结构体申请内存对齐,补齐的判别与结构体长度的计算
C语言的结构体大小计算