当前位置: 首页 > news >正文

C语言、自定义类型:联合体、枚举

📚 目录

  • 1.联合体声明定义
  • 1.联合体的特点
  • 1.联合体的内存大小
  • 4.联合体与结构体的对比
  • 5.联合体判断编译器的大小端
  • 6.枚举类型的声明
  • 7.枚举类型的优点
  • 8.枚举类型的使用


前言:
今天我们又来学习一种自定义类型:联合体;那么什么是联合体和枚举呢?接下来我们就来学习学习。




联合体(也可以成为共用体):联合体就像一个一个结构一样,就好像结构体,都是由多个成员组合而成,这些成员可以是不同的类型,关键字:union
特点:编译器只为最大的内存分配空间,所有成员共用一块内存空间;给联合体内任意一个成员赋值,其他成员的值也跟着发生改变。




1. 联合体的声明定义

接下来演示联合体的声明定义

#include<stdio.h>//联合体类型的声明unionpf{chara;intc;};intmain(){//联合体类型定义unionpf opp={0};return0;}

以上就是我们联合体简单的声明和定义。

🔙 返回目录




2. 联合体的特点

联合体的成员是共用一块内存空间的,联合体的内存大小至少是最大成员体的内存大小;只有这样才能保证每一个联合体成员都能够存得下。
我们通过Vs调试窗口内存来探究他的结果:
代码1:

#include<stdio.h>//联合体类型的声明unionpf{chara;intc;};intmain(){//联合体类型定义unionpf opp={0};//打印每个成员的地址printf("%p\n",&opp);printf("%p\n",&(opp.a));printf("%p\n",&(opp.c));return0;}

代码2:

#include<stdio.h>//联合体类型的声明unionpf{chara;intc;};intmain(){//联合体类型定义unionpf opp={0};opp.c=0x11223344;opp.a=0x55;printf("%x\n",&(opp.a));return0;}


代码1:我们发现了他们三个的结果都是相同的第一个地址。
我们再看看他opp.c的内存和opp.a的内存地址。



代码2:我们发现了原本opp.c这个位置原本上应该存放的是0x11223344这里的44被opp.a里面的0x55给占用了。
从结果上看,我们得到的地址都是相同的地址,这就说明了联合体每个成员的内存大小都是共用的。

联合体共用内存情况:

4个字节分别对应着4个地址。

🔙 返回目录




3. 联合体的内存大小

那么我们联合体的内存大小是怎么算的呢?
联合体的大小最小为最大成员的内存大小。
当联合体中最大内存成员的大小不是最大对齐数的整数倍的时候,就要对齐到最大对齐数的整数倍。

例如:

//计算下列结构体的大小。#include<stdio.h>unionpf1{chara[5];intc;};unionpf2{shorta[7];intc;};intmain(){printf("%zu\n",sizeof(unionpf1));printf("%zu\n",sizeof(unionpf2));return0;}

结果:

为什么会是这个结果呢?我们来分析一下。

🔙 返回目录



4.结构体与联合体的对比

那么结构体和联合体有什么区别呢?

structS{charc;inti;};unionUn{charc;inti;};#include<stdio.h>intmain(){structSs={0};unionUn un={0};return0;}


我们通过图片可以知道结构体的内存浪费比较大,而我们联合体浪费的内存远远没有结构体那么多。当我们结构体里面内存非常多的时候,浪费的内存也会不断增多。
而我们的联合体采用的是共用内存空间的形式,对于内存的利用比较高。
总结:联合体可以适当减少内存,但是当我们给其中一个成员赋值的时候,其他成员的值也会发生改变。

🔙 返回目录



联合体判断编译器的大小端

#include<stdio.h>inttest(){union{//建立一个联合体inti;charc;}un;un.i=1;returnun.c;//因为是联合体所以c和i的内存是共用的,我们返回char类型的c让他访问一个字节。返回1是小端返回0是大端}intmain(){intr=test();if(r==1){printf("小端\n");}else{printf("大端\n");}return0;}


我们使用的Vs编译器为小端。

🔙 返回目录



枚举类型:
枚举:就是一个一个把可能的值给列举出来。
就像我们生活中星期一到星期天、月份、颜色、价格等等这些东西给一一列举出来。像这些数字我们就能够使用枚举给他们列出来。
在以后写代码过程中避免不了大量的代码,代码一多就会出现各种各样的问题。

例如:(以订单为例子) ```c#include<stdio.h>//我们用#defind定义了一些毫无关系的常量#defineORDER_PENDING_PAYMENT1#defineORDER_PENDING_DELIVERY2#defineORDER_DELIVERED3#defineORDER_COMPLETED4voidList(intstatus){switch(status){caseORDER_PENDING_PAYMENT:printf("订单待付款\n");break;caseORDER_PENDING_DELIVERY:printf("订单待发货\n");break;case30:printf("订单已发货\n");break;caseORDER_COMPLETED:printf("订单已完成\n");break;default:printf("状态未知\n");break;}}intmain(){List(3);return0;}

问题1:常量无归类,代码量大了后难以管理
问题2:容易写错值(比如把3写成30),编译器无法校验
问题3:无法直观看出这些常量是一组的
调用时只能传数字,语义不清晰

6.枚举类型的声明

举例我们上面的例子:

#include<stdio.h>enumDay{Mon,Tues,Wed,Thur,Fri,Sat,Sun};

颜色

enumColor{RED,GREEN,bLUE};

注意:
我们每写完一个枚举成员用逗号隔开而不是分号,最后一个枚举成员不用添加分号。
在枚举成员{ }外面必须添加分号。
我们定义的枚举类型的成员可能都是有值的,默认从1开始,依次加1在声明枚举类型的时候我们可以进行赋值。

例如:

enumColor{RED=3,GREEN=4,bLUE=6};

当我们进行赋值完成后,在使用过程中就类似#defind定义常量,如果只对第一个进行了赋值,那么后面的就会在第一个的基础上加1。

enumColor{RED=9,GREEN,//这里就会变成10bLUE// 这里就会变成11};
🔙 返回目录



7.枚举类型的优点

我们知道了#defind也能定义常量,为什么还会有枚举呢?
我们就要学学枚举的优点了。
优点:
增加我们代码的可读性和可维护性;#define 定义的常量是全局的,无归属关系,易命名冲突。
相比较#defind我们的枚举有类型检查,更加严谨。
枚举变量本质是整型变量,所以可以用%d输出其数值。
枚举成员是编译期常量,不能修改
便于调试。我们编译器在编译过程中会删掉#defind定义的符号。

🔙 返回目录



8.枚举类型的使用

例如:

enumColor{RED=1,GREEN=2,BLUE=3};intmain(){enumColorr=GREEN;//使⽤枚举常量给枚举变量赋值return0;}
🔙 返回目录



完!

http://www.jsqmd.com/news/494357/

相关文章:

  • DeepSeek LeetCode 699. 掉落的方块 public List<Integer> fallingSquares(int[][] positions)
  • GraphRAG开源生态全景:6大主流开源项目,微软/蚂蚁/港大项目同台PK
  • 软件综合项目笔记
  • 2026 最新解读:AI 在数字资产管理中的 5 大应用场景与实践路径
  • DeepSeek LeetCode 710. 黑名单中的随机数 public Solution(int n, int[] blacklist) Java实现
  • 个人笔记机器学习2
  • 70.爬楼梯
  • R ∪ S(并集)**:正确合并了 R 和 S 的所有元组,并去重((b,a,d) 和 (d,f,g) 在两者中均出现,只保留一次
  • 【ZooKeeper】 ZooKeeper面试必知必会:从基础到进阶的全方位指南
  • SEH详解(六)
  • PCIe-FC补充《PCI Express Technology 3.0》Chapter 6 Flow Control
  • Netty[ NIO 核心速成 ] ---- NIO三大组件(Channel Bufferselector)
  • AI赋能森林火防助力开启智慧守护新篇章,基于最新以注意力为核心的YOLOv12全系列【n/s/m/l/x】参数模型开发构建AI智能化森林火防无人机巡检场景下森林火点、烟雾异常检测预警系统
  • 走上管理岗,一定要学会立威
  • java工具:《Java字符串处理:如何获取指定字符第N次出现的位置?》
  • STM32 学习 —— 个人学习笔记9-1(USART串口协议 串口发送及接收数据)
  • 461.汉明距离
  • 附录A 游戏推广运营实战:《暗黑王朝》的市场化之路
  • GESP三级历年真题解析(原码、反码和补码)
  • leetcode 困难题 1402. Reducing Dishes 做菜顺序
  • 2026年热门的AI品牌管理品牌推荐:AI品牌管理系统/AI品牌营销管理系统实力公司推荐 - 品牌宣传支持者
  • leetcode 1405. Longest Happy String 最长快乐字符串-耗时100
  • 计算机毕设 java 梅州红色文化传承小程序 Java+SpringBoot 梅州红色文化小程序 微信小程序红色文化传承平台
  • 2026 独立开发者 AI 工具栈:我的选择和理由
  • 从交易者到“合伙人”:Cber经纪人体系全解析,你的每一份共识都算数
  • 5个免费IP查询API对比:哪个最适合你的项目?(附性能测试数据)
  • ChatTTS下载安装全攻略:从原理到避坑指南
  • 2026年知名的AI品牌视频公司推荐:AI品牌宣传片/AI品牌营销管理/AI品牌营销管理系统品牌公司推荐 - 品牌宣传支持者
  • FreeRTOS工程项目实践
  • 计算机毕设 java 美文推荐系统 Java+SpringBoot 美文推荐分享平台 Web 版美文博文交流网站