结构体传参
struct S { int data [ 1000 ]; int num ; }; struct S s = {{ 1 , 2 , 3 , 4 }, 1000 }; // 结构体传参 void print1 ( struct S s ) { printf ( "%d\n" , s . num ); } // 结构体地址传参 void print2 ( struct S * ps ) { printf ( "%d\n" , ps -> num ); } int main () { print1 ( s ); // 传结构体 print2 ( & s ); // 传地址 return 0 ; }
上面的 print1 和 print2 函数哪个好些?
答案是:首选 print2 函数。
原因:
函数传参的时候,参数是需要压栈,会有时间和空间上的系统开销。
如果传递一个结构体对象的时候,结构体过大,参数压栈的的系统开销比较大,所以会导致性能的下降。
结论:
结构体传参的时候,要传结构体的地址。
位段
位段的声明和结构体是类似的,有两个不同:
位段的成员必须是 int、unsigned int 或signed int 。
位段的成员名后边有一个冒号和一个数字。
如图:
A就是一个位段。
计算:位段是按比特位的大小来进行计算的,比如一个字节有8个比特位,存入的时候根据数据类型的不同计算出相应的比特位依次往后存储,若存储不下则开辟下一个字节
举个例子:
那么8这个数字是怎么来的呢?是这样的:
int 型具有四个字节,共32个比特位,故存储时将前三个放入第一块空间中,由于第四个是30个比特位存储不下,因此开辟下一块空间存储,即开辟了两块空间,就是好8个字节。
注意:
和结构体相比,位段可以达到同样的效果,但是可以很好地节省空间,但是有跨平台的问题存在。
跨平台问题:
枚举的声明
枚举顾名思义就是一一列举。把可能的取值一一列举。
比如我们现实生活中:
一周的星期一到星期日是有限的7天,可以一一列举
性别有:男、女、保密,也可以一一列举。
月份有12个月,也可以一一列举
这里就可以使用枚举了。先上代码:
enum Day // 星期 { Mon , Tues , Wed , Thur , Fri , Sat , Sun }; enum Sex // 性别 { MALE , FEMALE , SECRET } ; enum Color // 颜色 { RED , GREEN , BLUE };
enum Day、enum Sex、enum Color都是枚举类型。
而{}里边的是枚举的可能取值,叫做枚举常量
这些可能取值都是有值的,默认从0开始,一次递增1。
当然,在定义的时候也可以赋初值。像这样:
enum Color // 颜色 { RED = 1 , GREEN = 2 , BLUE = 4 };
枚举的优点
我们可以使用 define 定义常量,为什么非要使用枚举?
原因如下:
1. 增加代码的可读性和可维护性
2. 和define定义的标识符比较枚举有类型检查,更加严谨。
3. 防止了命名污染(封装)
4. 便于调试
5. 使用方便,一次可以定义多个常量
枚举的使用
enum Color // 颜色 { RED = 1 , GREEN = 2 , BLUE = 4 }; enum Color clr = GREEN ; // 只能拿枚举常量给枚举变量赋值,才不会出现类型的差异。 clr = 5 ; //ok??
只能拿枚举常量给枚举变量赋值,才不会出现类型的差异。
联合体
联合也是一种特殊的自定义类型
这种类型定义的变量也包含一系列的成员,特征是这些成员公用同一块空间(所以联合也叫共用体)。
比如:
// 联合类型的声明 union Un { char c ; int i ; }; // 联合变量的定义 union Un un ; // 计算连个变量的大小 printf ( "%d\n" , sizeof ( un ));
联合体的声明
大小的特点:
联合的成员是共用同一块内存空间的,这样一个联合变量的大小,至少是最大成员的大小(因为联
合至少得有能力保存最大的那个成员。
union Un { int i ; char c ; }; union Un un ; // 下面输出的结果是一样的吗? printf ( "%d\n" , & ( un . i )); printf ( "%d\n" , & ( un . c )); // 下面输出的结果是什么? un . i = 0x11223344 ; un . c = 0x55 ; printf ( "%x\n" , un . i );
大小的计算:
当最大成员大小不是最大对齐数的整数倍的时候,就要对齐到最大对齐数的整数倍。
union Un1 { char c [ 5 ]; int i ; }; union Un2 { short c [ 7 ]; int i ; }; // 下面输出的结果是什么? printf ( "%d\n" , sizeof ( union Un1 )); printf ( "%d\n" , sizeof ( union Un2 ));
以上就是我对自定义类型的相关讲解,讲解有不清楚或者讲错的地方,可以在评论区或者私信.看完记得点赞哦!!!