位段的声明和结构是类似的,有两个不同:
1.位段的成员 必须是int,unsigned int或signed int。
2.位段的成员名后边有一个冒号和一个数字(通常是相同类型,可以有char)
位段的内存分配,节省空间
1位段的成员可以是int或者是char(属于整型家族)类型
2.位段的空间上是按照需要以4个字节(int)或一个字节(char)的方式来开辟的。
3.位段涉及很多不确定因素,位段是不跨平台的,注重可移植的程序,应该避免使用位段。
位段:二进制位 1Byte=8bit
struct S
{
int_a:2;//2个二进制位,两个bit
int_b:5;
int_c:10;
int_d:30;
};
int main()
{
struct S s;
printf("%dn",sizeof(s));//8个字节
return 0;
}
位段的跨平台问题:
- int位段被当成有符号数还是无符号数是不确定的。位段中最大位的数目不能确定(16位机器最大16,32位机器最大32,写成27,在16位机器会出问题)。位段中成员在内存中从左向右分配,还是从右向左分配标准尚未定义。
4.当一个结构包含两个位段,第二个位段成员比较大,无法容纳于第一个位段剩余的位时,是舍弃剩余的位还是利用,这是不确定的。
枚举
enum Sex
{
MALE, //MALE=0, 枚举默认从0开始,依次增1
FEMALE, //枚举的可能取值:常量
SECRET //MALE=2, 也可给常量赋初始值,而后不可更改
};
int main()
{
enum Sex s=MALE;//拿枚举常量给枚举变量赋值,才不会出现类型的差异
s=FEMALE; //只能赋值这三个元素,不能赋除枚举类以外的
return 0;
}
enum Color
{
RED, //0
GREEN, //9 若给GREEN赋初值9
BLUE //10
};
#define RED 0
int mian()
{
int color=0;//该句是错误的,枚举类型!=int类型
printf("%d %d %dn",RED,GREEN,BLUE);
return 0;
}
枚举的优点:大小都是4个字节
可以使用#define定义常量,为何使用枚举?
联合的特点:
联合的成员是共用同一块内存空间的,这样一个联合变量的大小至少是最大成员的大小(因为联合至少得有能力保存最大的那个成员)成员间是不能同时使用的。
check-sys()
{
int a=1;
return *(char*)&a;//返回1,表示小端;返回0,表示大端。
}
int check-sys()
{
union Un
{
char c;
int i;
}u;
u.i=1;
return u.c;
}
int main()
{
int a=1;
int ret=check-sys();
if(1==*(char*)&a)
{
printf("小端n");
}
else
{
printf("大端n");
}
联合大小的计算:
联合的大小至少是最大成员的大小,当最大成员大小不是最大对齐数的整数倍的时候,就要对齐到最大对齐数的整数倍。
union Un
{
int a;
char arr[5]; //对齐数是1
};
int main()
{
union Un u;
printf("%dn",sizeof(u)); //浪费3个字节,最大对齐数是8
}



