精华内容
下载资源
问答
  • 结构体对齐规则

    2019-07-28 18:42:26
    结构体对齐

    结构体:

    结构体(struct)是由一系列具有相同类型或不同类型的数据构成的集合。因为这一特性,方便了开发者在使用的过程中可以将需要的不同的数据类型放在一起,做成我们需要的数据类型,通过结构体封装一些属性来组成新的类型。在我们实现链表的时候也很好的体现了这一点

    但是,结构体在使用的过程中需要格外的注意!!!

    结构体的大小及对齐规则:

    结构体的大小不是结构体体中数据简单的相加,因为我们主流的计算机使用的都是32bit字长的CPU,对这类型的CPU取4个字节的数要比取一个字节要高效、方便。这就是内存对齐的由来。
    每个平台上的编译器都有自己的默认“对齐系数”(也叫对齐模数)。开发者也可以通过预编译命令#pragma pack(n),n=1,2,4,8,16来改变这一系数,n为指定的“对齐系数”。

    结构体对齐规则:

    1、结构体(struct)的数据成员,第一个数据成员放在offset为0的位置,以后每个数据成员在对齐数的整数倍的位置。
    对齐数=编译器默认的对齐数与该成员大小的较小值。
    VS中默认对齐数为8,linux默认对齐数为4.
    2、结构体总大小为最大对齐数(每个成员都有一个对齐数)的整数倍。
    3、如果嵌套了结构体的情况,嵌套的结构体对齐到自己的最大对齐数的整数倍处,结构体的整体大小就是所有最大对齐数(含嵌套结构体的对齐数)的整数倍。

    struct A
    {
    	int a;
    	char b;
    	double c;
    };
    //sizeof(A)=16;
    
    struct B
    {
    	char b;
    	double c;
    	int a;
    };
    
    
    //sizeof(B)=24
    

    struct A和struct B里面的数据除了顺序不同,里面的数据是一样的,但是编译之后发现它们的结构体长度是不一样的。所以数据的顺序不同结构体的对齐方式也不同,结构体的大小自然不同

    struct A :a是4字节,b是1字节,不符合对齐规则,所以b自动补全3个字节刚好和a加起来是8字节完成对齐,c是8字节,所以加起来是16字节

    struct B :b是一个字节,不符合对齐规则,不全7个字节完成对齐,c是8个字节,b是4个字节,不符合对齐规则,不全4个字节完成对齐,所以struct B的大小是24

    在这里插入图片描述

    展开全文
  • C语言结构体对齐规则与0字节数组@[TOC](C语言结构体对齐规则与0字节数组)C语言结构体对齐规则对齐规则说明 C语言结构体对齐规则 不同的编译器和系统默认的对齐规则会有差异,这里我使用的32bit的MinGW。 对齐规则...

    C语言基础:结构体对齐规则与0字节数组


    • 不同的编译器和系统默认的对齐规则会有差异,这里我使用的win32的MinGW
    • C语言结构体一般是默认四字节对其的。

    结构体对其规则

    一般的,C语言结构体默认是以4字节对其方式,以此默认4字节为依据,结构体对其规则有以下三项:

    • 规则一:struct内的第一个成员在偏移地址0处,随后成员的偏移地址在其本身类型大小整数倍处
    • 规则二:struct的总大小为内部最大成员类型的整数倍
    • 规则三:当A结构内含有结构B时,B在A中的偏移地址为B结构内最大元素类型的大小的整数倍

    示例1:

    #include <stdio.h>
    #include <stdlib.h>
    #include <stdint.h>
    
    #define debug_printf(value) printf(#value " ---==> %d\n", value)
    
    #define struct_member_offset(struct, member) (((char *)(&(((struct *)0)->member))) - ((char *)0))
    
    typedef struct
    {
    	uint8_t  a;    // 偏移地址0
    	uint32_t b;    // 偏移地址4
    	uint8_t  c;    // 偏移地址8
    	uint8_t  d;    // 偏移地址9
    }test_t;
    
    int main()
    {
    	int a = struct_member_offset(test_t, a);
    	int b = struct_member_offset(test_t, b);
    	int c = struct_member_offset(test_t, c);
    	int d = struct_member_offset(test_t, d);
    	debug_printf(sizeof(test_t));
    	debug_printf(a);
    	debug_printf(b);
    	debug_printf(c);
    	debug_printf(d);
    	return 0;
    }
    
    

    输出结果:

    解析:

    • a为第一个成员在偏移地址0处
    • b成员类型为无符号整形占用四字节,根据规则一b要对齐到4字节地址处,所以偏移地址为4,相当于在a成员后面补齐了3字节,不过这补齐的3个字节没用到
    • c和d成员大小都为1字节,根据规则一要对齐到1字节,所以c偏移为9,d偏移为10
    • 四个成员目前所占用的空间加起来是10字节,但是!此时还没完!根据规则二结构体的总大小为结构内最大成员的整数倍,test_t这个结构内最大成员是b占用4字节,所以10字节还要补齐2字节去对齐4字节,所以sizeof(test_t)=12。

    示例二:

    现在将d成员改为uint64类型:

    typedef struct
    {
    	uint8_t  a;
    	uint32_t b;
    	uint8_t  c;
    	uint64_t  d;
    }test_t;
    

    输出结果:

    还是根据规则解析:

    • a在偏移地址0处
    • b在4处
    • c在8处
    • abc所占用的空间为9个字节,d为uint64类型占8个字节,所以要对齐到8字节处,也就是偏移地址16处,相当于c成员后补齐了7字节。
    • 目前四个成员所占用的空间为24字节,24是d类型的倍数大小,所以sizeof(test_t)=24

    示例三:
    现在将结构改为如下,多了一个数据

    typedef struct
    {
    	uint8_t  a;
    	uint32_t b;
    	uint8_t c[3];
    	uint8_t  d;
    	uint64_t  e;
    }test_t;
    
    

    输出结果:

    c成员为3字节,占用偏移地址8,9,10三个空间,所以总大小还是24。


    示例四:
    将结构改为如下,现在test_t结构内包含结构sub_t。

    typedef struct
    {
    	uint8_t sub_a;
    	uint32_t sub_b;
    }sub_t;
    
    typedef struct
    {
    	uint8_t  a;
    	uint32_t b;
    	sub_t c;
    	uint8_t  d;
    	uint64_t  e;
    }test_t;
    

    输出结果:

    解析:

    • 根据规则一和二解析sizeof(sub_t)=8字节
    • 根据规则三确定sub_t在test_t中的偏移地址肯定是4的整数倍处,所以c这个结构成员偏移地址为8
    • d偏移地址为17
    • e偏移地址为24
    • sizeof(test_t)=32

    字节为0的数组与结构体

    先看一下0字节数组的大小:

    int main()
    {
    	int array[0];
    	debug_printf(sizeof(array));
    	return 0;
    }
    

    输出结果:

    sizeof(array) ---==> 0
    

    说明0字节数据占用空间为0,那么看下面这个例子:

    #include <stdio.h>
    #include <stdlib.h>
    #include <stdint.h>
    
    #define debug_printf(value) printf(#value " ---==> %d\n", value)
    
    #define struct_member_offset(struct, member) (((char *)(&(((struct *)0)->member))) - ((char *)0))
    
    typedef struct
    {
    	uint8_t  a;
    	uint32_t b;
    	uint8_t  c;
    	uint64_t  d[0];
    }test_t;
    
    int main()
    {
    	int a = struct_member_offset(test_t, a);
    	int b = struct_member_offset(test_t, b);
    	int c = struct_member_offset(test_t, c);
    	int d = struct_member_offset(test_t, d);
    	debug_printf(sizeof(test_t));
    	debug_printf(a);
    	debug_printf(b);
    	debug_printf(c);
    	debug_printf(d);
    	return 0;
    }
    

    输出结果:

    !!奇怪的问题出现了!!

    但道理说d成员占用空间为0,sizeof(test_t)应该是12才对,但是sizeof(test_t)却是16!!

    原因:d成员虽然占用空间为0,但是他是uint64类型的,结构体的总大小是按照内部最大成员进行对齐的!test_t对齐到了8字节,所以sizeof(test_t)的大小为16字节!


    ends…

    展开全文
  • 【IoT】STM32 结构体对齐规则

    千次阅读 2019-04-01 09:18:40
    在相同的对齐方式下,结构体内部数据定义的顺序不同,结构体整体占据内存空间也不同。 如下结构体定义: struct A { // a 的自身对齐值为 4,偏移地址为 0x00~0x03,a 的起始地址 0x00 满足 0x00%4=0 int a; // ...

    1、对齐算法

    在相同的对齐方式下,结构体内部数据定义的顺序不同,结构体整体占据内存空间也不同。

    如下结构体定义:

    struct A {
    // a 的自身对齐值为 4,偏移地址为 0x00~0x03,a 的起始地址 0x00 满足 0x00%4=0
    int a;
    
    // b 的自身对齐值为 1,由于紧跟 a 之后的地址,即 0x04 满足 0x04%1=0,所以 b 存放在 0x04 地址空间
    char b;
    
    // c的自身对齐值为2,由于紧跟b之后的地址0x05%2不是0,而0x06%2=0
    // 因此c的存放起始地址为0x06,存放在0x06~0x07空间。
    // 在b和c之间的0x05地址则补空字节
    short c;
    };

    结构体A中包含:

    1)4 字节长度的 int;

    2)1 字节长度的 char;

    3)2 字节长度的 short 型数据一个。

    所以 A 用到的空间应该是 7 字节。

    但是因为编译器要对数据成员在空间上进行对齐,由于结构体自身对齐值取数据成员中自身对齐值的最大值,即 4,并且 0x00~0x07 的 8 字节空间满足 8%4=0,所以 sizeof(strcut A) 值为 8。

    现在把该结构体调整成员变量的顺序:

    struct B {
    // b的自身对齐值为1,其起始地址为0x00,由于满足0x00%1=0,所以b存放在0x00地址空间
    char b;
    
    // a的自身对齐值为4,由于紧跟b之后的地址0x01%4不是0,而0x04%4=0
    // 因此c的存放起始地址为0x04,存放在0x04~0x07空间。
    // 在b和a之间的0x01~0x03地址则补3个空字节。
    int a;
    
    // c的自身对齐值为2,由于紧跟a之后的地址0x08%2=0,因此c的存放起始地址为0x08,存放在0x08~0x09空间        
    short c;          
    };

    这时候同样是总共7个字节的变量,但是由于结构体自身对齐值取数据成员中自身对齐值的最大值,即4;

    并且0x00~0x09的10字节空间不满足10%4=0,而12%4=0,所以sizeof(struct B)的值却是12,即在紧跟c之后的0x0A~0x0B地址还需补两个空字节,使得整个结构体占用的字节空间为12个字节。
     
    下面我们使用预编译指令#pragma pack (value)来告诉编译器,使用我们指定的对齐值来取代缺省的。

    #pragma pack (2) /*指定按2字节对齐,等价于#pragma pack(push,2)*/
    struct C {
    char b;
    int a;
    short c;
    };

    #pragma pack () /*取消指定对齐,恢复缺省对齐,等价于#pragma pack(pop)*/
    sizeof(struct C) 值是8。

    修改对齐值为1:

    #pragma pack (1) /*指定按1字节对齐*/
    struct D {
    char b;
    int a;
    short c;
    };

    #pragma pack () /*取消指定对齐,恢复缺省对齐*/

    sizeof(struct D) 值为7。

    对于char型数据,其自身对齐值为1,对于short型为2,对于int,float,long类型,其自身对齐值为4,double,long long类型,其自身对齐值为8单位字节。

    2、四个概念值

    1)数据类型自身的对齐值,就是上面交代的基本数据类型的自身对齐值;

    2)指定对齐值:#pragma pack (value)时的指定对齐值value;

    3)结构体或者类的自身对齐值:其数据成员中自身对齐值最大的那个值;

    4)数据成员、结构体和类的有效对齐值:自身对齐值和指定对齐值中小的那个值;

    有了这些值,我们就可以很方便的来讨论具体数据结构的成员和其自身的对齐方式。

    有效对齐值N是最终用来决定数据存放地址方式的值,最重要。

    有效对齐N,就是表示“对齐在N上”,也就是说该数据的"存放起始地址%N=0"。

    而数据结构中的数据变量都是按定义的先后顺序来排放的。

    第一个数据变量的起始地址就是数据结构的起始地址。

    结构体的成员变量要对齐排放,结构体本身也要根据自身的有效对齐值圆整,就是结构体成员变量占用总长度需要是对结构体有效对齐值的整数倍。

    这样就不难理解上面的几个例子的值了。

    例子分析:

    struct B {
    char b;
    int a;
    short c;
    };

    假设B从地址空间0x0000开始排放。

    该例子中没有定义指定对齐值,该值默认为4。

    第一个成员变量b的自身对齐值是1,比指定或者默认指定对齐值4小,所以其有效对齐值为1,所以其存放地址0x0000符合0x0000%1=0.

    第二个成员变量a,其自身对齐值为4,所以有效对齐值也为4,所以只能存放在起始地址为0x0004到0x0007这四个连续的字节空间中,符合0x0004%4=0, 且紧靠第一个变量。

    第三个变量c,自身对齐值为2,所以有效对齐值也是2,可以存放在0x0008到0x0009这两个字节空间中,符合0x0008%2=0。所以从0x0000到0x0009存放的都是B内容。

    再看数据结构B的自身对齐值为其变量中最大对齐值(这里是a)和指定对齐值(这里是4)中较小的那个,所以就是4,所以结构体的有效对齐值也是4。

    根据结构体圆整的要求,0x0009到0x0000=10字节,(10+2)%4=0。

    所以0x0000A到0x000B也为结构体B所占用,故B从0x0000到0x000B共有12个字节,sizeof(struct B)=12;、

    #pragma pack (2) /*指定按2字节对齐*/
    struct C {
    char b;
    int a;
    short c;
    };

    #pragma pack () /*取消指定对齐,恢复缺省对齐*/

    第一个变量b的自身对齐值为1,指定对齐值为2,所以,其有效对齐值为1,假设C从0x0000开始,那么b存放在0x0000,符合0x0000%1=0;

    第二个变量,自身对齐值为4,指定对齐值为2,所以有效对齐值为2,所以顺序存放在0x0002、0x0003、0x0004、0x0005四个连续字节中,符合0x0002%2=0。

    第三个变量c的自身对齐值为2,所以有效对齐值为2,顺序存放在0x0006、0x0007中,符合0x0006%2=0。
    所以从0x0000到0x00007共八字节存放的是C的变量,又C的自身对齐值为4;
    所以C的有效对齐值为2。又8%2=0,C只占用0x0000到0x0007的八个字节。所以sizeof(struct C)=8.
     
    更改c编译器的缺省字节对齐方式:

    在缺省情况下,c编译器为每一个变量或数据单元按其自然对界条件分配空间;

    一般地可以通过下面的两种方法来改变缺省的对界条件:

    方法一:

    使用#pragma pack(n),指定c编译器按照n个字节对齐;
    使用#pragma pack(),取消自定义字节对齐方式。

    方法二:

    __attribute(aligned(n)),让所作用的数据成员对齐在n字节的自然边界上;

    如果结构中有成员的长度大于n,则按照最大成员的长度来对齐;

    __attribute((packed)),取消结构在编译过程中的优化对齐,按照实际占用字节数进行对齐。

    比如:

    typedef struct
    
    {
      ...
    
    }__attribute__((aligned(4))) param_t;

    3、示例

    例子一:

    #pragma pack(4)
    class TestB
    {
       public:
       int aa;   //第一个成员,放在[0,3]偏移的位置,
      char a;    //第二个成员,自身长为1,#pragma pack(4),取小值,也就是1,所以这个成员按一字节对齐,放在偏移[4]的位置。由于下一成员short b是按2字节对齐,因此char a后面只需补一个空字节
      short b; //第三个成员,自身长2,#pragma pack(4),取小值为2,按2字节对齐,所以放在偏移[6,7]的位置。
      char c;   //第四个,自身长为1,放在[8]的位置。
    };

    可见,此类实际占用的内存空间是9个字节。

    根据规则5,结构整体的对齐是min( sizeof( int ), pack_value ) = 4,所以sizeof( TestB ) = 12; 

    char a 占用一个字节,后面补3个空字节;

    short b和char c可以放在同一4字节空间中,后面只需补一个空字节。

    例子二:

    #pragma pack(2)
    class TestB
    {
       public:
          int aa;   //第一个成员,放在[0,3]偏移的位置,
      char a;   //第二个成员,自身长为1,#pragma pack(4),取小值,也就是1,所以这个成员按一字节对齐,放在偏移[4]的位置。由于下一成员short b按2字节对齐,因此char a后面只需补一个空字节
      short b; //第三个成员,自身长2,#pragma pack(4),取2,按2字节对齐,所以放在偏移[6,7]的位置。
      char c;   //第四个,自身长为1,放在[8]的位置。
    };

    可见结果与例子一相同,各个成员的位置没有改变,此时结构整体的对齐是min( sizeof( int ), pack_value ) = 2,所以sizeof( TestB ) = 10;char a后面补一个空字节;char c后面补一个空字节。

    例子三:

    #pragma pack(4)
    class TestC
    {
      public:
         char a;    //第一个成员,放在[0]偏移的位置,由于下一成员short b按2字节对齐,因此char a后面只弱补一个空字节
      short b; //第二个成员,自身长2,#pragma pack(4),取2,按2字节对齐,所以放在偏移[2,3]的位置。
      char c;   //第三个,自身长为1,放在[4]的位置。
    };

    整个类的实际内存消耗是5个字节,整体按照min( sizeof( short ), 4 ) = 2对齐,所以结果是sizeof( TestC ) = 6。

    例子四:

    struct Test
    {
        char x1;   //第一个成员,放在[0]位置。由于下一成员short x2按2字节对齐,因此char x1后面只需补一个空字节,
        short x2; //第二个成员,自身长度为2,按2字节对齐,所以放在偏移[2,3]的位置,
        float x3;  //第三个成员,自身长度为4,按4字节对齐,所以放在偏移[4,7]的位置,
        char x4;  //第四个成员,自身长度为1,按1字节对齐,所以放在偏移[8]的位置,
    };

    所以整个结构体的实际内存消耗是9个字节,考虑到结构整体的对齐是4个字节,所以整个结构占用的空间是12个字节。char x1和short x2共用一个4字节空间,后面补一个空字节;char x4后面需要补3个空字节。

    例子五:

    #pragma pack(8)
    
    struct s1
    {
        short a; //第一个,放在[0,1]位置,
        long b;  //第二个,自身长度为4,按min(4, 8) = 4对齐,所以放在[4,7]位置
    };

    所以结构体的实际内存消耗是8个字节;

    结构体的对齐是min( sizeof( long ), pack_value ) = 4字节,所以整个结构占用的空间是8个字节。

    struct s2
    {
    char c;         //第一个,放在[0]位置,
    s1 d;           //第二个,根据规则四,对齐是min( 4, pack_value ) = 4字节(由于s1占用了8个字节,这里为什么不是8字节??),所以放在[4,11]位置,
    long long e; //第三个,自身长度为8字节,所以按8字节对齐,所以放在[16,23]位置,
    };

    所以实际内存消耗是24字节。整体对齐方式是8字节,所以整个结构占用的空间是24字节。

    #pragma pack()

    所以:sizeof(s2) = 24, char c后面是空了3个字节接着是s1 d, s1 d后面又补了4个空字节,char c占一个字节,后面补7个字节;s1 d占8个字节;long long e占8个字节。

     

     

     


    refer:

    https://www.cnblogs.com/King-Gentleman/p/5297355.html

     

     


     

    展开全文
  • C/C++结构体对齐规则

    2020-12-22 20:54:00
    1.基本理解  比如:struct TEST  {  char a;  int b;  char c;  }  那么经过sizeof后得出结果是 12, 因为默认内存占用4byte, 变量a占用1byte,剩下3个,不足以存放变量b,故变量a也占用了4byte, ...
  • 结构体对齐规则及位域规则

    千次阅读 2019-04-28 22:53:43
    对齐规则如下图:共占12个字节 关于3 和 4规则 的运用: struct S3 { double d ; //0- 7 char c ; //8 //8-11被占用 int i ; //12-15 } ; //16 struct S4 { char c1 ; //0 //...

    让我们看看下面两个代码:

    struct S1
    {
    	char c1;//1
    	int i;//4
    	char c2;//1
    };
    
    struct S2
    {
    	char c1;//1
    	char c2;//1
    	int i;//4
    
    };
    int main()
    {
    	struct S1 s1 = { 0 };
    	printf("%d\n", sizeof(struct S1));
    	printf("%d\n", sizeof(s1));
    	printf("%d\n", sizeof(struct S2));
    	system("pause");
    	return 0;
    }
    

    得出的结果会不会是一样的呢?
    让我们看下结果:
    在这里插入图片描述
    答案是否定的。

    造成这样的原因是:结构体对齐

    结构体对齐的规则:

    • 1.第一个成员在与结构体偏移量为0的地质处
    • 2.其他成员变量要对其到某个数字(对其数)的整数倍的地址处
      对齐数=编译器默认的一个对齐数与该成员大小的较小值(vs下为8, linux下为4)(#pragma (4、8) 可以用来控制默认对齐数的大小)
    • 3.结构体总大小为最大对齐数(每个成员都有一个对齐数)的整数倍
    • 4.如果出现嵌套情况,嵌套的结构体对齐到自己的最大对齐数的整数倍处,结构体的整体大小就是所有最大对齐数(含嵌套结构体的对齐数)的整数倍。

    对齐规则如下图:共占12个字节
    在这里插入图片描述

    关于3 和 4规则 的运用:

    struct S3
    {
    	double d;//0- 7
    	char c;//8
    	//8-11被占用
    	int i;//12-15
    };//16
    
    struct S4
    {
    	char c1;//0
    	//占用0-7
    	struct S3 s3;
    	//占用8 - 23
    	double d;//23 - 31
    
    };//总计32
    	printf("%d\n", sizeof(struct S3));
    	printf("%d\n", sizeof(struct S4));
    	printf("%d\n", offsetof(struct S4, c1));
    	printf("%d\n", offsetof(struct S4, s3));
    	printf("%d\n", offsetof(struct S4, d));
    

    结果
    在这里插入图片描述

    为什么存在对其?

    1.平台原理(移植问题):不是所有硬件平台都能访问任意地址上的任意数据的;某些硬件平台只能在某些地址处取某些特定类型的数据,否则抛出异常
    2.性能问题:数据结构应该尽可能的在自然边界上对齐。原因在于,为了访问未对齐的内存,处理器需要两次内存访问,而对齐的只需要一次。

    位域:

    位域 :必须有“int”、“signed int”或“unsigned int”类型但是很多编译器都对类型有拓展。
    规则:
    -1.如果相邻位域字段的类型相同,且其位宽之和小于类型的sizeof的大小,则后面的字符将紧邻前一个字段存储,直到不能容纳为止。

    • 2.如果相邻位域的类型相同,但其位宽之和大于类型的sizeof大小,则后面的字段将从新的存储单元开始,其偏移量为其类型大小的整数倍。
    • 3.如果相邻的位域字段的类型不同,不同的编译器具体实现有差异,VC6采取不压缩的方法,Dev-c++,gcc的压缩方式
    • 4.如果位域字段之间穿插着非位域字段,则不压缩。
    • 5.整个结构体的大小为最宽基本类型成员大小的整数倍。

    例子:

    struct A
    {
    	char    a : 2;
    	char    b : 3;
    	char    c : 1;
    };
    
    struct B
    {
    	char    a : 2;
    	char    b : 3;
    	char    c : 7;
    };
    
    struct C
    { 
    	unsigned a : 19;
    	unsigned b : 11;
    	unsigned c : 4;
    	unsigned d : 29;
    	char index;
    };
    
    struct D 
    {
    	char    a : 2;
    	char    b : 8;
    	int		c : 1;
    };
    
    struct E
    {
    	int i : 8;
    	int j : 4;
    	double b;
    	int a : 3;
    };
    
    struct F
    {
    	int i : 8;
    	int j : 4;
    	char b : 1;
    	int a : 3;
    };
    
    int main()
    {
    	printf("%d\n", sizeof(A));
    	printf("%d\n", sizeof(B));
    	printf("%d\n", sizeof(C));
    	printf("%d\n", sizeof(D));
    	printf("%d\n", sizeof(E));
    	printf("%d\n", sizeof(F));
    
    
    	system("pause");
    }
    

    在这里插入图片描述

    展开全文
  • c语言结构体对齐规则

    2017-09-07 09:11:44
    1.第一个成员在与结构体变量偏移量为0的地址处。 2.其他成员变量要对齐到某个数字(对齐数)的整数倍的地址处。 //对齐数 = 编译器默认的一个对齐数 与...4.如果嵌套了结构体的情况,嵌套的结构体对齐到自己的对齐数
  • C语言结构体字节对齐规则

    千次阅读 多人点赞 2019-04-12 10:55:40
    C语言结构体字节对齐规则 基本规则 规则1 :结构体(struct)的数据成员,第一个数据成员放在offset为0的地方,以后每个数据成员存放在offset为该数据成员大小的整数倍的地方(比如int在32位机为4字节,则要从4的...
  • 结构体字节对齐和瑞萨编译器中结构体对齐的设置
  • 结构体对齐规则-计算结构体的大小 结构体中的成员可以是不同的数据类型,成员按照定义时的顺序依次存储在连续的内存空间。和数组不一样的是,结构体的大小不是所有成员大小简单的相加,需要考虑到系统在存储结构体...
  • 结构体字节对齐规则

    2018-01-29 11:17:59
    结构体字节对齐规则,主要是介绍结构体字节对齐规则,内容有点长,但是很全面.
  • 详解C语言结构体对齐(内存对齐问题)C语言结构体对齐也是老生常谈的话题了。内容虽然很基础,但一不小心就会弄错。我在刚开始接触的时候也会是很迷糊,通过编译器运行的结果总是和自己的不一样,使自己很苦恼。在网上...
  • 1. 结构体内存对齐规则   对齐数 = 编译器默认的一个对齐数 与 该成员大小的较小值   vs中的默认值为8; Linux中的默认值为4; 原则1:数据成员的对齐规则(以最大的类型字节为单位)。   结构体(struct)的...
  • 结构体对齐是为了更加快速的读取结构体中的变量。对齐之后,多余的内存空间被“填充”了,其中不放任何数据。
  • C 结构体字节对齐规则

    千次阅读 2018-01-29 11:10:32
    文档下载:结构体字节对齐规则 原则1:数据成员的对齐规则(以最大的类型字节为单位)。 结构体(struct)的数据成员,第一个数据成员放在offset为0的地方,以后每个数据成员存放在offset为该数据成员大小的整数倍的...
  • gcc结构体对齐

    2017-04-09 10:20:06
    struct A a= //gcc支持的一种...{ //结构体变量对齐存放,所以a的大小为8字节  .a=4,  .b=555, } // 定义类型的同时定义变量,s1是一个变量。 struct student {  char name[20];  int age; }s
  • 为什么要进行内存对齐(以空间换时间) 为了有助于加快计算机的取数速度,编译器默认会对结构体进行处理(实际上其 它地方的数据变量也是如此),让宽度为2的基本数据类型(short等)都位于能被2整除的...结构体对齐...
  • C-结构体对齐

    千次阅读 2016-09-23 19:28:58
    技术群的筒子们有时候会提到结构体对齐,说实话这个问题还不是几句...首先是结构体对齐规则: 1、对于n个字节的元素,它的首地址要能被n整除  eg:int—4个字节的元素,它为结构体的第一个元素时,起始地址应能被4整除
  • 基本概念 CPU一次能读取多少个字节的数据主要是看数据总线是多少位的,16位CPU一次...那么对于下面这个结构体: struct st { char c; int i; }; 如果不进行对齐操作,char 的地址范围0x00000000,int的地址范围为0x0
  • 什么是字节对齐 这跟读取数据有关,cpu读取一次能读取到的内存大小跟数据总线的位数有关,如果数据总线为16位,那么cpu一次能够读取2字节;如果为32位那么cpu一次可以读取4字节,而读取数据是需要消耗时间的,为了...
  • 0x00简介首先要知道结构体的对齐规制1.第一个成员在结构体变量偏移量为0的地址处2....如果嵌套了结构体的情况,嵌套的结构体对齐到自己的最大对齐数的整数倍处,结构体的整数体大小就是所有最大对齐数(含...
  • 结构体对齐规则 规则一:结构体中元素是按照定义顺序一个一个放到内存中去的,但并不是紧密排列的。从结构体存储的首地址0开始,每一个元素放置到内存中时,它都会认为内存是以自身类型大小来划分的,因此元素放置的...

空空如也

空空如也

1 2 3 4 5 ... 20
收藏数 19,376
精华内容 7,750
关键字:

结构体对齐规则