有关结构体,位段,枚举,联合体的介绍
结构体的介绍:结构体是一些值的集合,这些值称为成员变量,每个成员可以是不同类型。
声明一个学生类型,属性:名字+电话+年龄。
struct stu
{
char name[10];
char telnumber[30];
int age;
};
struct stu
{
char name[10];
char telnumber[30];
int age;
}wuhu;//全局变量
struct stu3;//全局变量
int main()
{
struct stu stu1;//局部变量
struct stu stu2;//局部变量
return 0;
}
typedef struct stu
{
char name[10];
char telnumber[30];
int age;
}wuhu;//typedef将stu重命名为wuhu
struct
{
char a[20];
int b;
}x;//只能使用结构体声明后创建的变量,不能创建新的变量
struct A
{
int a;
struct A a;//err 这里会无限套娃
};
struct B
{
int a;
struct B* next;//结构体的自引用只能是指针
};
typedef struct stu
{
char name[10];
char telnumber[30];
char a;
int age;
}wuhu;
int main()
{
wuhu a = { "abcde","1234",'a',10 };
return 0;
}
要计算结构体的大小首先要了解结构体的对齐规则
例如:
typedef struct stu
{
char name[10];
char a;
int age;
}wuhu;
上述结构体类型中char name[10]可以看成10个char类型,在32位平台中一个char占1个字节 vs 中默认对齐数位8,1和8对比1比较小对齐数取1,char name[10]占10个字节a也是char所以也占一个字节 。 age为int类型对齐数为4所有只能放在4为倍数的地址处,而name[10]与a加起来占11个字节不是4的倍数所以age只能放在12地址处所以总大小为12+4=16 16 16是4的倍数所以wuhu的大小为16。
为什么存在内存对齐?
大部分的参考资料都是这么说的(没有官方解释)
所以当我们声明结构体时为了减少浪费让占用空间小的尽量集中在一起。
代码如下
#pragmaticpack(4);//设置对齐数为4
#pragmaticoack();//取消设置的默认对齐数
代码如下
#include
offsetof(struct S,c);//struct S为定义类型,c是需要计算偏移量的元素。
位段的介绍:
1.位段的成员必须是int,unsigned int,或signed int
2.位段的成员名后面的有一个冒号和一个数字。
struct A
{
int a : 2;
int b : 5;
int c : 10;//分号后面是内存分配 大小是字节
int d : 30;
};
1.int位段被当成有符号数还是无符号数是不确定的。
2.位段中最大位的数目不能确定,(16位机器最大16,32位机器最大32,写成27,在16位机器会出问题)。
3.位段中的成员在内存中从左向右分配,还是从右向左分配标准尚未定义。
4.当一个结构体包含两个位段,第二个位段成员比较大,无法容纳于第一个位段的位时,是舍弃剩余的位还是利用,这是不确定的。
总结:和结构体相比,位段可以达到同样的效果,但是可以很好的节省空间,但是有跨平台的问题存在。
枚举就是一一列举,如星期有星期1到星期天,月份有1~12月。
enum Sex
{
MALE = 2,
FEMALE = 3,
SECRET=0
};
上述代码中enum为枚举的关键字 Sex为枚举类型,MALE, FEMALE, SECRET为枚举可能的取值,可赋值(但值不可修改)也可以不赋值(不赋值默认第一个为0后面依次加1)。
enum Sex
{
MALE = 2,
FEMALE = 3,
secret=0
};
int main()
{
enum Set s = MALE;//只能赋值MALE,FEMALE,AECRET
return 0;
}
为什么使用枚举?
我们可以使用#define定义常量,为什么要用枚举?
union Un
{
char i;
int j;
};
上述代码中 union 为联合体的关键字 Un为类型i和j不能同时存在。