09 字节对齐_结构体数组
- 一、sizeof关键字
-
- [1.1 基本类型的sizeof](#1.1 基本类型的sizeof)
- [1.2 数组类型的sizeof](#1.2 数组类型的sizeof)
- [1.3 结构体类型的sizeof](#1.3 结构体类型的sizeof)
- 二、字节对齐--结构体对齐
-
- [2.1 结构体对齐](#2.1 结构体对齐)
- [2.2 对齐规则](#2.2 对齐规则)
-
- 2.2.1对其参数规则
- [2.2.2 数据成员对齐规则](#2.2.2 数据成员对齐规则)
- [2.2.2.3 结构体的总大小](#2.2.2.3 结构体的总大小)
- [2.2.2.4 结构体嵌套](#2.2.2.4 结构体嵌套)
- 三、typedef关键字
-
- [3.1 对已有类型定义别名](#3.1 对已有类型定义别名)
- [3.2 一维数组类型的定义格式](#3.2 一维数组类型的定义格式)
- [3.3 二维数组类型的定义格式](#3.3 二维数组类型的定义格式)
- [3.4 结构体的定义格式](#3.4 结构体的定义格式)
- 四、作业
一、sizeof关键字
1.1 基本类型的sizeof
可以适用类型,也可以适用变量
1.2 数组类型的sizeof
1.3 结构体类型的sizeof
二、字节对齐--结构体对齐
2.1 结构体对齐
- 例1
c
struct Test
{
char a;
int b ;
};
int main(int argc, char* argv[]){
Test t;
printf("%d\n",sizeof(t));
printf("%d\n",sizeof(Test));
return 0;
}
- 例2
c
struct Test
{
int a ;
__int64 b ;
char c ;
};
int main(int argc, char* argv[]){
Test t;
printf("%d\n",sizeof(t));
printf("%d\n",sizeof(Test));
return 0;
}
8的倍数
- 例3
c
struct Test
{
int a ;
__int64 b ;
char c ;
char d ;
};
int main(int argc, char* argv[]){
Test t;
printf("%d\n",sizeof(t));
printf("%d\n",sizeof(Test));
return 0;
}
2.2 对齐规则
2.2.1对其参数规则
c
#pragma pack( n )
struct AA{
//......
}
#pragma pack( )
1.对齐参数:n为字节对齐数,其取值为1、2、4、8,默认是8。
2.如果这个值比结构体成员的sizeof值小,那么该成员的偏移量应该以此值为准,即是说,结构体成员的偏移量应该取二者的最小值.
对其操作为:
2.2.2 数据成员对齐规则
结构的数据成员,第一个数据成员放在offset为0的地方,以后每个数据成员存储的起始位置要从该成员大小的整数倍开始(比如int在32位机为4字节,则要从4的整数倍地址开始存储).
2.2.2.3 结构体的总大小
结构体的总大小,也就是sizeof的结果,必须是其内部最大成员的整数倍,不足的要补齐。
2.2.2.4 结构体嵌套
如果一个结构里有某些结构体成员,则结构体成员要从其内部最大元素大小的整数倍地址开始存储。如(struct a里存有struct b,b里有char,int,double等元素,那b应该从8的整数倍开始存储.)
三、typedef关键字
typedef为C语言的关键字,作用是为一种数据类型定义一个新名字。这里的数据类型包括内部数据类型(int,char等)和自定义的数据类型(struct等)。
3.1 对已有类型定义别名
c
typedef unsigned char BYTE;
typedef unsigned short WORD;
typedef unsigned int DWORD;
3.2 一维数组类型的定义格式
c
typedef int vector[10];
int main(int argc, char* argv[])
{
vector v;
v[0] = 1;
v[1] = 2;
v[2] = 3;
v[3] = 4;
v[4] = 5;
return 0;
}
3.3 二维数组类型的定义格式
typedef int name[5][5];
c
typedef int nameTable[5][5][5];
int main(int argc, char* argv[])
{
matrix v;
nameTable n;
v[0][0] = 1;
v[0][1] = 2;
v[0][2] = 3;
v[0][3] = 4;
v[0][4] = 5;
n[0][0][0] = 1;
return 0;
}
3.4 结构体的定义格式
c
typedef struct student
{
int x;
int y;
}stu;
四、作业
- 代码
c
#include <stdio.h>
#include <string.h>
struct Point{
float x;
float y;
float z;
};
struct Monster{
char name[30];
int level;
int ID;
int damage;
int blood;
Point point;
};
Monster monster[10];
void Assignment(){
strcpy(monster[0].name, "这是一个精英怪");
monster[0].level = 20;
monster[0].ID = 1001;
monster[0].damage = 18;
monster[0].blood = 360;
monster[0].point.x = 20.1;
monster[0].point.y = 20.1;
monster[0].point.z = 20.1;
}
void Print(){
printf("怪物的名字是:%s\n", monster[0].name);
printf("怪物的等级是:%d\n", monster[0].level);
printf("怪物的ID是:%d\n", monster[0].ID);
printf("怪物的伤害是:%d\n", monster[0].damage);
printf("怪物的血量是:%d\n", monster[0].blood);
printf("怪物的位置x坐标是:%f\n", monster[0].point.x);
printf("怪物的位置y坐标是:%f\n", monster[0].point.y);
printf("怪物的位置z坐标是:%f\n", monster[0].point.z);
}
int main(int argc, char* argv[]){
Assignment();
Print();
return 0;
}
- 顺便画个字节对齐分析图
共计一个Monster结构体大小为60字节。
printf("%d\n", sizeof( monster[0]));得到60
printf("%d\n", sizeof(Monster));得到60
- 顺便反汇编看看