位段
位段关键字: struct
位段与结构体关键字相同,性质也相似,不过也存在着一些不同。
1、位段的声明
位段的声明与结构体有两点不同:
1、位段内的成员类型必须为:char、int、unsigned int 或 signed int。
2、位段的成员名后面由 一个冒号和一个数字 组成。(数字代表每个变量所占的位数bit,即所占内存大小)
声明示例:
//声明
struct AA
{
int _a:2; //_a的大小为2bit,即两个二进制位大小
int _b:5;
int _c:10;
int _d:30;
}; //struct AA 就是一个位段类型
//位段的使用方法与结构体相同
struct AA n1 = {0};
n1._a = 1;
n1._b = 12;
n1._c = 3;
n1._d = 4;
(一般一个位段内的成员保持同一类型。)
位段除了 成员大小是可以自定义的 以外跟结构体没什么区别,用法也是相同的,即位段就是成员大小可自定义的结构体。但由于跨平台可能不兼容等问题,位段更多用于一些特定情景,结构体的可应用面更宽。
2、位段的内存分配
1、位段的成员类型决定了位段中内存一次开辟的大小,int(一次开辟四个字节),char(一次开辟一个字节)。
2、若一次开辟的内存不够储存所有的成员,那就再开辟一次,直至将所有的成员存放完成。(实际上内存是一下子开辟好的,上面的说法是利于理解的一种解释)
3、由于不同的平台中,数据在内存中的存储方式不一定相同,比如一次开辟的内存无法储存下一个完整的变量,那这块空间剩余的部分是舍弃,还是继续用是不确定的。此外还有种种原因,所以位段的大小可能不相同。
枚举
枚举类型:一个把可能的取值一一列举出来的类型。
枚举关键字: enum
1、枚举类型的定义
enum Workday//工作日
{
MON, //除最后一个,其余均以 , 结尾
TUES, //可以赋值也可以不赋值
WED,
THUS,
FRI
};
enum Color//颜色
{
RED,
GREEN,
BLUE
};
以上定义的 enum Workday , enum Color 都是枚举类型。
枚举{ }中的内容是枚举类型的可能取值,也叫 枚举常量 。枚举类型定义的变量只能从枚举常量中取值。
这些可能取值都是有值的,默认从0开始,依次递增1,在定义的时候也可以自己赋初值。
2、枚举类型的使用
enum Color//颜色
{
RED = 1,
GREEN = 2,
BLUE = 4
};
enum Color clr = GREEN;//只能拿枚举常量给枚举变量赋值
其实,枚举更多的使用是:
需要定义同一类型(属性)的多个常量时,用枚举代替#define
3、枚举类型的优点
枚举的优点:
- 增加代码的可读性和可维护性
- 和#define定义的标识符比较枚举有类型检查,更加严谨。
- 防止了命名污染(封装)
- 便于调试
- 使用方便,一次可以定义多个常量
联合(共用体)
1、联合类型的定义
联合类型定义的变量也包含一系列的成员,特征是这些成员共用同一块空间(所以联合也叫共用体)。
联合关键字: union
//联合类型的声明
union Un
{
char c;
int i;
};
//联合变量的定义
union Un u1;
2、联合的特性
联合的成员共用同一块内存空间,因此联合中的一个成员发生改变,其他的成员也会受到影响,所以一个联合中的成员一次只能使用其中一个,不能同时使用两个及以上。
3、联合的大小
联合大小的计算:
- 联合的大小至少是最大成员的大小。
- 当最大成员大小不是最大对齐数的整数倍时,就要对齐到最大对齐数的整数倍。
union Un1
{
char c;
int i;
};
union Un2
{
short c[5];
int i;
};
printf("%d\n", sizeof(union Un1)); //大小为 4
printf("%d\n", sizeof(union Un2)); //大小为 12