【C语言】自定义类型:联合与枚举的简明概述

请添加图片描述
🔥引言

关于自定义类型除了我们常用的结构体,还有联合与枚举也是属于自定义类型。本篇将简单介绍联合与枚举基本概念和使用方法

请添加图片描述

Alt

🌈个人主页:是店小二呀
🌈C语言笔记专栏:C语言笔记
🌈C++笔记专栏: C++笔记

🌈喜欢的诗句:无人扶我青云志 我自踏雪至山巅
请添加图片描述


一、联合体(Union)

1.1 联合体的声明

联合体是一个或多个成员组成,其中成员可以是不同类型,并且所有成员共用同一块内存空间,所以联合体也称为共用体。联合体声明的关键字是union。

//联合体类型的声明
union Un
{
    char c;
    int i;
};
int main()
{
    union Un un;//联合体的定义
    sizeof("%d\n,sizeof(un)");-->4
    return 0;
}

1.2 联合体的特点

联合体的特点:

  • 联合体所有成员共用同一块内存空间,一个联合体变量的大小,至少是最大成员的大小,编译器只为最大的成员分配足够大的空间
  • 给联合体其中一个成员赋值,其他成员的值也会变化
代码一
union Un
{
    char c;
    int i;
};
int main()
{
    union Un un = {0};
    // 下⾯输出的结果是⼀样的吗?
    printf("%p\n", &(un.i));
    printf("%p\n", &(un.c));
    printf("%p\n", &un);
    return 0;
}

结果:001AF85C
    001AF85C
    001AF85C
代码二
union Un
{
    char c;
    int i;
};
int main()
{
    union Un un = {0};

    un.i = 0x11223344;
    un.c = 0x55;
    printf("%x\n", un.i);
    return 0;
}
结果:11223355

在这里插入图片描述

说明】:
从代码一输出的结果是相同的,说明联合体中成员变量是一块空间存储。从代码二输出中,第四个字节的内容被修改位55,对联合体中成员赋值,会影响联合体的全部成员,char类型只占用一个字节。

1.3 结构体和联合体内存布局对比

struct Su
{
    char c;
    int i;
}S;
Union Un
{
    char c;
    int i;
}un;

在这里插入图片描述

说明】:结构体是通过以为空间换取时间设计("浪费"空间),而联合体是节省空间


1.4 计算联合体的大小

规则如下】:

  • 联合体的大小至少是最大成员的大小
  • 当最大成员大小(联合体总大小)要对齐到最大对齐数的整数倍
#include <stdio.h>
union Un1
{
    char c[5]; 1 8 1//最大成员大小为5
        int i;  4 8 4
};//最大对齐数位4,最大成员大小为5,对齐到8是最大对齐数的整数倍

union Un2
{
    short c[7]; 2 8 2//最大成员大小为7
        int i;  4 8 4
};//最大对齐数位4,最大成员大小为7,对齐到16是最大对齐数的整数倍

int main()
{
    printf("%d\n", sizeof(union Un1));-->8
    printf("%d\n", sizeof(union Un2));-->16
    return 0;
}

1.5 联合体的实际使用样例

场景如下,搞一个礼品兑换,礼品兑换单中有三种商品:图书、被子、衬衫。每一种商品的信息:库存量、价格等相关的其他信息

  • 图书:书名、作者、页数
  • 杯子:设计
  • 衬衫:设计、可选颜色、尺寸

如果单纯采用结构体,将变量全部写下来:

struct list
{
    int stock_number;//库存量
    double price;//定价
    int item_type;//商品类型

    char title[20];//书名
    char author[20];//作者
    int num_pages;//页数
    char design[30]//设计
        int colors;//颜色
    int sizes;//尺寸   
}

优点】:

  • 设计简单,使用方便

【缺点】:

  • 包含了各种的属性,内存占用比较大、浪费空间也加大了
  • 部分属性信息是常用的,有些商品不需这部分信息

解决办法:】把公共属性单独写出来,剩余属于各种商品本身的属性使用联合体处理,再一定程度上节省了内存

配合上联合体设计:

struct gift_list
{
    int stock_number;//库存量
    double price; //定价
    int item_type;//商品类型
    union{
        struct
        {
            char title[20];//书名
            char author[20];//作者
            int num_pages;//⻚数
        }book;
        struct
        {
            char design[30];//设计
        }mug;
        struct
        {
            char design[30];//设计
            int colors;//颜⾊
            int sizes;//尺⼨
        }shirt;
    }item;
};

说明】:

将不同商品的本身属性使用联合体处理,初始化的时候是初始化一个联合体对象,联合体里面只支持初始化一个结构体成员,没法加中括号,再在中括号里面分别初始化,语法不允许

而且这种情况我们正常使用时本身就只会选择一个成员进行初始化。如果需要初始化多个对象,则将其放进一个结构体数组初始化,每个数组元素都是结构体单独初始化

联合体习题】:判断当前机器是大端还是小端(通过数字和地址关系)

int check_sys()
{
    union
    {
		int i;
        char c;
    }
    un.i=1;//00 00 00 01-->01 00 00 00(小端)
    return un.c 
}

二、Enum(枚举)

枚举顾名思义就是⼀>列举

列举可能的取值:用于定义一组具有离散值的常量,使数据更简洁、方便使用,关枚举的关键字enum。

2.1 枚举类型的声明

比如列举:星期一到星期日十有限的七天或者性别、颜色等。

enum Day
{
    Mon,
    Tues,
    Wed,
    Thur,
    Fri,
    Sat,
    Sun
};
enum Sex
{
    Man;
    Woman;
}

以上定义的enum Day、enum Sex都是枚举类型,而{}中枚举类型的可能取值称为枚举常量

在声明枚举类型的时候,可以同时对枚举常量初始化(枚举常量都是有值的,默认从0开始,并且依次递增)

enum Sex
{
    Man=10;
    Woman;//11
}

2.2 枚举类型的优点

问题】:

这里就像#define定义常量,为什么还有枚举这样子数据类型

枚举的优点】:

  1. 增加代码的可读性和可维护性
  2. 枚举类型有类型检查,更加严谨
  3. 便于调试,预处理阶段会删除#define定义的符号
  4. 一次可以定义多个枚举常量,使用方便
  5. 枚举常量是遵循作用域规则的,枚举声明在函数内,只能在函数内使用

2.3 枚举类型的使用

enum Color
{
	Red=2;
    Blue=1;
}
enum Color clr=Blue;

使用枚举常量给枚举变量赋值,也可以拿整数给枚举变量赋值(C语言可以,C++不行,C++检查比较严格)

使用场景】:

比如:在枚举类型中定义事物的编号,通过输入数字(编号),找到对应的事情

enum color
{
    Red=1;
    Blue;//1递增为2
}
int main()
{	
    enum color favorite_color;
    printf("请输入你喜欢的颜色:(1.Red,2.Bule)");
    //输入1或2去代表Red或Bule
    scanf("%u",&favorite_color);
    switch(favorite_color)
    {
        case Red(Red==1):
            printf("%你喜欢的颜色为红色");
            break;
        case Blue(Blue==2):
            printf("%你喜欢的颜色为蓝色");
            break;
        default :
            printf("没有喜欢的颜色")
    } 
}

【说明】:这里不是输入枚举对象,而是枚举对象对应的数字。


在这里插入图片描述
以上就是本篇文章的所有内容,在此感谢大家的观看!这里是店小二C语言笔记,希望对你在学习C语言中有所帮助!

  • 126
    点赞
  • 101
    收藏
    觉得还不错? 一键收藏
  • 打赏
    打赏
  • 81
    评论

“相关推荐”对你有帮助么?

  • 非常没帮助
  • 没帮助
  • 一般
  • 有帮助
  • 非常有帮助
提交
评论 81
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包

打赏作者

是店小二呀

你的鼓励将是我创作的最大动力

¥1 ¥2 ¥4 ¥6 ¥10 ¥20
扫码支付:¥1
获取中
扫码支付

您的余额不足,请更换扫码支付或充值

打赏作者

实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值