自定义类型部分知识理解
1:结构体
结构体:一些值得集合,这些值是它的但结构体各个成员可能具有不同的类型。
结构变量属于标量类型,所以你可以像对待其他标量类型一样执行相同类型的操作。
结构体声明:
eg:
struct Stu
{
int a;
char b;
float c;
double d;
}
Stu称作标签,是和这些成员列表联系起来的,标签不是变量,但可以使用标签来创建变量;
eg:
struct Stu x;
struct Stu y[10],*p;
你可以用标签创建结构体数组和结构体指针。
eg:
struct
{
int a;
char b;
float c;
double d;
}x,y[10],*p;
这种声明方式中,x,y[0],*p,都是变量,并且不要把结构体理解为数组,两个很不一样,数组中元素类型都是一样的,而结构体不一定都一样。
所以p = &x,这种表达式是非法的。
也可以用这种声明方式:
typedef struct
{
charname[20];//名字
intage;//年龄
charsex[5];//性别
char id[20];//学号
}Stu;
用typedef创建一个新的类型,这样后面声明就可以这样声明了:
Stu x;
Stu y[10],*p;
j结构体成员也可以包含其他结构体;结构体成员的访问可以用(.)操作符来访问的
eg:
struct Stu x;
strcpy(x.name, "zhangsan");//使用.访问name成员
x.age = 20;//使用.访问age成员
struct Stu
{
charname[20];//名字
intage;//年龄
charsex[5];//性别
char id[20];//学号
};
struct Stu x = {"lisan",20,"nan",100};//初始化
结构体内存对齐:
看到这种现象你就要了解结构体内存是怎么回事。
对其规则:
1. 第一个成员在与结构体变量偏移量为0的地址处。
2. 其他成员变量要对齐到某个数字(对齐数)的整数倍的地址处。
对齐数 = 编译器默认的一个对齐数与该成员大小的较小值。
VS中默认的值为8
Linux中的默认值为4
3. 结构体总大小为最大对齐数(每个成员变量除了第一个成员都有一个对齐
数)的整数倍。
4. 如果嵌套了结构体的情况,嵌套的结构体对齐到自己的最大对齐数的整数倍处,结构体的整体大小就是所有最大对齐数(含嵌套结构的对齐数)的整数倍
eg:
总结:结构体内存对齐就是用空间换时间
位段:
位段的声明和任何普通的结构成员声明相同,但不同的是,位段声明为int,signed int ,或unsigned int类型。其次在成员名后面是一个冒号和一个整数。
这个整数是指定该位段所占用的位的数目。
eg:
structA
{
int_a:2;
int_b:5;
int_c:10;
int
_d:30;
};
printf("%d",sizeof(struct A));值是8;
一个int 型有32位,前三个占17位,放_d三十位是很明显不够了,所以根据编译器可选择把_d放在下一个字节或者紧更着_c.
跟结构相比,位段可以达到同样的效果,但是可以很好的节省空间,但是有跨平台的问题存在。
为了节省空间尽可能的将奇数位放在一块。
枚举
枚举就是把可能的取值一一列举出来。
eg:
枚举成员变量不赋初值默认从0开始逐渐加1,也可以赋值
当GREEN赋值为4时,后面值就随前面值加1;
总结:枚举可以增加代码的可读性和可维护性,使用起来方便,可以定义多个常量
联合
联合中所有成员公用一块空间;
eg:
因为它公用一块内存空间,int为最大的4字节,所以联合变量的大小至少为最大成员的大小。
eg:
此时最大成员大小为2*7=14,14不是最大对齐数的整数倍,所以联合成员大小为16;