• linkedu视频
  • 平面设计
  • 电脑入门
  • 操作系统
  • 办公应用
  • 电脑硬件
  • 动画设计
  • 3D设计
  • 网页设计
  • CAD设计
  • 影音处理
  • 数据库
  • 程序设计
  • 认证考试
  • 信息管理
  • 信息安全
菜单
linkedu.com
  • 网页制作
  • 数据库
  • 程序设计
  • 操作系统
  • CMS教程
  • 游戏攻略
  • 脚本语言
  • 平面设计
  • 软件教程
  • 网络安全
  • 电脑知识
  • 服务器
  • 视频教程
  • JavaScript
  • ASP.NET
  • PHP
  • 正则表达式
  • AJAX
  • JSP
  • ASP
  • Flex
  • XML
  • 编程技巧
  • Android
  • swift
  • C#教程
  • vb
  • vb.net
  • C语言
  • Java
  • Delphi
  • 易语言
  • vc/mfc
  • 嵌入式开发
  • 游戏开发
  • ios
  • 编程问答
  • 汇编语言
  • 微信小程序
  • 数据结构
  • OpenGL
  • 架构设计
  • qt
  • 微信公众号
您的位置:首页 > 程序设计 >C语言 > 解析C语言中结构体struct的对齐问题

解析C语言中结构体struct的对齐问题

作者: 字体:[增加 减小] 来源:互联网 时间:2017-05-28

通过本文主要向大家介绍了c语言typedef struct,c语言中struct用法,c语言中struct,c语言struct,c语言struct用法等相关知识,希望对您有所帮助,也希望大家支持linkedu.com www.linkedu.com

首先看一下结构体对齐的三个概念值:

数据类型的默认对齐值(自身对齐):
1.基本数据类型:为指定平台上基本类型的长度。如在32位机器中,char对齐值为1,short为2,int,float为4,double为8;
结构体:其数据成员中默认对齐值最大的那个值。
2.指定对齐值:#pragma pack (value)时的指定对齐值value。
3.数据类型的有效对齐值:默认对齐值和指定对齐值中小的那个值。
有了这些值,我们就可以很方便的来讨论具体数据结构的成员和其自身的对齐方式。有效对齐值N是最终用来决定数据存放地址方式的值,最重要。有效对齐N,就是表示“对齐在N上”,也就是说该数据的“偏移量%N=0”。而数据结构中的数据变量都是按定义的先后顺序来排放的。第一个数据变量的起始地址就是数据结构的起始地址。结构体的成员变量要对齐排放(对于非对齐成员需要在其前面填充一些字节,保证其在对齐位置上),结构体本身也要根据自身的有效对齐值圆整(就是结构体总长度需要是结构体有效对齐值的整数倍)。

通过上面的分析,对结构体进行字节对齐,我们需要知道四个值:

  • 指定对齐值:代码中指定的对齐值,记为packLen;
  • 默认对齐值:结构体中每个数据成员及结构体本身都有默认对齐值,记为defaultLen;
  • 成员偏移量:即相对于结构体起始位置的长度,记为offset;
  • 成员长度:结构体中每个数据成员的长度(注结构体成员为补齐之后的长度),记为memberLen。

及两个规则:

1.对齐规则:
offset % vaildLen = 0,其中vaildLen为有效对齐值vaildLen = min(packLen, defaultLen);

2.填充规则:
如成员变量不遵守对齐规则,则需要对其补齐;在其前面填充一些字节保证该成员对齐。需填充的字节数记为padLen:

padLen = getPadLen(offset , defaultLen);
int getPadLen(int offsetLen, int defaultLen)
{
  int vaildLen = min(packLen,defaultLen);
  if(0 == vaildLen || 0 == offsetLen % vaildLen)
  {
    return 0;
  }
  return vaildLen - (offsetLen % vaildLen);
}
</div>

结构体对齐算法思想:深度优先填充

先对齐内层结构体;
对每个数据成员计算其defaultLen、memberLen和offset;

再遍历每个数据成员时计算;
对于基本数据类型成员defaultLen=memberLen;对于结构体成员defaultLen等于它的所有成员的最大的memberLen;
遍历时对成员的memberLen进行累加,得到当前成员的offsetLen;
运用对齐及填充规则:在当前结构体成员前填充padLen个字节;


举例说明:

struct{

 short a;

 short b;

 short c; }A; sizeof(A) = 6; 
</div>

(vc6与gcc相同)

struct{

 long a;

 short c; }A; sizeof(A) = 8;

</div>

(vc6与gcc相同), 它的内存分配为: a1 a2 a3 a4 , c1 c2 x x(a1为a的第一个字节,x为补齐字节,下同)

struct{

int a;

char b;

short c; }A;

sizeof(A) = 8;

</div>

A的内存分配为:

 a1 a2 a3 a4, b1 x c1 c2
</div>
struct{

char a;

int b;

short c; }A1;

sizeof(A1) = 12;

</div>

(vc6与gcc相同)

A1的内存分配为:

a1 x x x, b1 b2 b3 b4, c1 c2 x x
</div>

下面是更复杂的情况,结构体作为成员

struct{

int a;

doubl b;

short c; }A; // sizeof(A) = 24 (vc6与gcc相同)

struct{

  char a,b;

int c;

double d;

short e;

struct A h;

}B;

sizeof(B) = 48 //(vc6与gcc相同)

</div>

A的内存分布:

a1 a2 a3 a4 x x x x, b1 b2 b3 b4 b5 b6 b7 b7, c1 c2 x x x x x x
</div>

B的内存分布:

a1 b1 x x, c1 c2 c3 c4 , d1 d2 d3 d4 d5 d6 d7 d8, e1 e2 x x x x 
</div>

</div>
分享到:QQ空间新浪微博腾讯微博微信百度贴吧QQ好友复制网址打印

您可能想查找下面的文章:

  • C语言中结构体(struct)的几种初始化方法
  • C语言 typedef:给类型起一个别名
  • 解析C语言中结构体struct的对齐问题
  • C语言中结构体struct编写的一些要点解析
  • C语言的Struct Hack笔记
  • typedef_struct与struct之间的区别
  • 深入解析C语言中typedef的四个用途
  • C语言typedef与复杂函数声明问题的深入解析

相关文章

  • 2017-05-28解析c++中的默认operator=操作的详解
  • 2017-05-28斐波那契数列 优化矩阵求法实例
  • 2017-05-28win32 api实现简单的消息窗口示例
  • 2017-05-28C++线性时间的排序算法分析
  • 2017-05-28C语言 实现N阶乘的程序代码
  • 2017-05-28C++进程间共享数据实例
  • 2017-05-28详解C++编程中多级派生时的构造函数和访问属性
  • 2017-05-28C语言中判断int,long型等变量是否赋值的方法详解
  • 2017-05-28C++中sprintf使用的方法与printf的区别分析
  • 2017-05-28有关C++继承与友元、继承与类型转换详解

文章分类

  • JavaScript
  • ASP.NET
  • PHP
  • 正则表达式
  • AJAX
  • JSP
  • ASP
  • Flex
  • XML
  • 编程技巧
  • Android
  • swift
  • C#教程
  • vb
  • vb.net
  • C语言
  • Java
  • Delphi
  • 易语言
  • vc/mfc
  • 嵌入式开发
  • 游戏开发
  • ios
  • 编程问答
  • 汇编语言
  • 微信小程序
  • 数据结构
  • OpenGL
  • 架构设计
  • qt
  • 微信公众号

最近更新的内容

    • C++设计模式之策略模式
    • C语言中的小数(float,double)
    • C++中拷贝构造函数的应用详解
    • C语言中getopt()函数和select()函数的使用方法
    • C语言 解决不用+、-、×、÷数字运算符做加法的实现方法
    • 详解C语言中的#define宏定义命令用法
    • C++编程中用put输出单个字符和cin输入流的用法
    • 浅析string类字符串和C风格字符串之间的区别
    • 利用C++的基本算法实现十个数排序
    • c语言操作文本的基本使用方法

关于我们 - 联系我们 - 免责声明 - 网站地图

©2020-2025 All Rights Reserved. linkedu.com 版权所有