一、结构体
1.1结构体的声明语法
struct 对象名
{
成员列表;
};
1.2结构体声明的解释
结构体其实与我们在数学中学过的集合本质相同
比如,现在有一个描述房子的集合,集合里有许多元素,有的元素描述房子的大小,有的元素描述房子的价格,还有的描述房子的装饰,这里的房子就是我们描述的对象,而其中的元素就是房子具有的属性
在结构体的声明中,struct是声明结构体的关键字,不可缺少,对象名就是我们想要描述的对象,对象可以是万事万物,比如学生可以是对象,内裤可以是对象,水可以是对象
成员列表其实就是对象的属性,我们可以用C语言内置的数据类型,如char,int,double等来描述对象具有的属性,比如
struct Student //声明一个结构体类型
{
int age; //年龄
double weight; //体重
char name; //名字
};
我们声明了一个学生类的结构体,在成员列表里,我们添加了学生的年龄,姓名,体重等属性
我们也可以将结构体类型作为学生的成员,但是不可以是学生这一类型(否则会无限套娃)
1.3建立结构体变量
在声明了某一对象的结构体之后,我们该如何创建该类型的变量呢?
比如我们上文声明了学生这一对象的结构体后,如何创建具体的学生对象
在我们声明了某一结构体后,struct 对象名 就是该结构体的数据类型,
因此struct Student就是我们定义好的自定义数据类型
1.3.1再声明了某一结构体后创建
结构体数据类型 变量名;
struct Student zs;//创建结构体变量,张三(zs)
从结构体变量的创建中,我们也可以看出结构体是某一事物的集合,只是一个泛指,可创建了该类型的变量后,泛指就成了特指
1.3.2在声明的同时创建
struct Student //声明一个结构体类型
{
int age; //年龄
double weight; //体重
char name; //名字
}ls;//李四(ls)就是我们在声明的时候创建的结构体变量,ls是变量名
1.3.3小技巧
如果你觉得结构体数据类型太长,可以用关键字typedef,来对结构体类型重命名
typedef struct Student //声明一个结构体类型
{
int age; //年龄
double weight; //体重
char name; //名字
}S;
//S等价于struct Student
1.4结构体变量的初始化
依旧拿学生这一对象说明
struct Student //声明一个结构体类型
{
int age; //年龄
double weight; //体重
char name; //名字
};
int main()
{
struct Student s1={18,60.0,"zhangsan"};
//结构体变量在初始化时,对该结构体的每个成员变量都要初始化,并且与成员
列表的顺序一一对应,字符串类型要使用引号,然后整体用括号括起来
}
1.5结构体的大小与内存对齐
提到结构体的大小那么就离不开内存对齐,
例如
struct Student //声明一个结构体类型
{
int age; //年龄
double weight; //体重
char name; //名字
};
该结构体的大小是多少呢?结构体的大小是像指针一样被具体定义呢,还是要
求得所有成员变量的大小之和呢
还是来讲讲内存对齐把,在声明结构体之后,
1.结构体的第一个成员变量的地址与结构体的起始地址相同,
2.其余变量取自身对齐数与编辑器对齐数的较小值的整数倍地址存储
这句话这么理解呢?就是说,我结构体自身是一个大房子,我的成员都在我的体内存储,而我的的第一个变量的存储地址和我的存储地址是相同的,其余的变量要按照某一个值的整数倍在我的地址中存储,而这个值就是成员变量自身的对齐数与编辑器对齐数的较小值,这个值会成为新的对齐数
成员变量的对齐数就是该变量所占字节大小,例如int占四个字节,那么这类型变量的对齐数就是4,(VS编辑器的对齐数是8)
假设每个长方形为一个字节,上述struct Student结构体内存对齐情况如下
3.结构体大小为最大对齐数的整数倍
存储int用了4个字节,浪费了4个字节,存储double是8个字节,char是一个字节,一个17个字节,int的对齐数为4,double为8,char为1,最大对齐数为8,
结构体大小取最大对齐数的整数倍并且能存储下17个字节,因此结构体最终大小为24个字节,调试结果如下