系列文章目录
🎈 🎈 我的优快云主页:OTWOL的主页,欢迎!!!👋🏼👋🏼
🎉🎉我的C语言初阶合集:C语言初阶合集,希望能帮到你!!!😍 😍
🔍🔍我的C语言进阶合集:我的C语言进阶合集,期待你的点击!!!🌈🌈
前言
各位博友,大家好!👋 今天我为大家分享C语言中的联合(
union
)和枚举(enum
)。
联合能存储不同数据类型,但需小心类型访问。
枚举为整数常量提供描述性名称,使代码更清晰。
我将详细介绍这两者的定义、语法及使用注意事项,助你轻松掌握!🚀
联合(union)
(1)定义
联合(
union
)是一种特殊的用户定义数据类型,它允许在相同的内存位置存储不同的数据类型。
联合变量的大小等于其最大成员的大小,所有成员共享同一块内存区域。
联合体的特点是所有成员共用 同⼀块内存空间。所 以联合体也叫:共用体。
这意味着在任何时候,联合只能存储其一个成员的值,
访问其他成员可能会导致未定义行为。
(2)语法
union UnionName
{
DataType1 member1;
DataType2 member2;
// 可以有更多成员
};
(3)使用注意事项
- 内存共享:联合的所有成员共享同一块内存,因此修改一个成员的值会影响其他成员的值(如果它们在同一内存位置重叠)。
- 访问限制:通常应记录当前存储了哪个成员的值,以避免读取未定义的数据。
- 对齐和填充:编译器可能会插入填充字节以满足对齐要求,这会影响联合的实际大小。
(4)示例
#include <stdio.h>
#include <string.h>
// 定义一个联合体 A,它包含一个整数、一个浮点数和一个字符数组
// 联合体的特性是所有成员共享同一块内存空间,因此最后一个赋值会覆盖前面的值
union A
{
int n; // 联合体成员,一个整数
double f; // 联合体成员,一个浮点数
char arr[10]; // 联合体成员,一个字符数组
};
int main()
{
union A a; // 声明一个联合体变量 a
//计算联合体变量 a 的所占内存大小
printf("%zd\n",sizeof(a));
// 给联合体的整数成员赋值,并打印
a.n = 66;
printf("Integer: %d\n", a.n);
// 给联合体的浮点数成员赋值,这会覆盖之前存储的整数
a.f = 5.20;
printf("Float: %f\n", a.f);
// 将字符串复制到联合体的字符数组成员,这会覆盖之前的浮点数
strcpy(a.arr, "Hello");
printf("arr: %s\n", a.arr);
// 注意:此时访问 a.n 或 a.f 是不安全的,因为它们的值已经被字符串覆盖,访问它们会得到未定义的行为
return 0;
}
(5)联合体的 ⼀ 个练习
写⼀个程序,判断当前机器是大端?还是小端?
int check_sys()
{
// 定义一个匿名联合体,包含一个整型成员和一个字符成员
union
{
int a; // 整型类型成员
char ch; // 字符类型成员
} un;
// 给联合体的整型成员赋值为 1
un.a = 1;
// 返回联合体的字符成员的值
// 如果系统是小端存储,那么'un.ch'将返回'1',因为小端存储的最低有效字节存储在最低的地址
// 如果系统是大端存储,那么'un.ch'将返回'0',因为大端存储的最高有效字节存储在最低的地址
return un.ch; // 返回1是小端,返回0是大端
}
- 解释:
这段代码的逻辑是这样的:整数1 在内存中的表示是
0x00000001
。
如果系统是小端存储,那么最低有效字节(即
0x01
)将存储在最低的地址,
因此通过联合体的字符成员un.ch
访问时,会得到0x01
,即1
。
如果系统是大端存储,那么最高有效字节(即
0x00
)将存储在最低的地址,
因此un.ch
将得到0x00
,即0
。通过这种方式,我们可以判断系统的字节序。
枚举(enum)
(1)定义
枚举(
enum
)是一种用户定义的类型,它由一组命名的整数常量组成。
枚举为这些常量提供了一个易于理解的名字,并使得代码更加清晰和可读。
(2)语法
enum EnumName
{
E1, // 默认为 0
E2, // 默认为 1
E3 = value, // 可以显式赋值
// 可以有更多枚举器,自动递增
};
(3)使用注意事项
- 默认值:
未显式赋值的枚举器从0开始递增。
- 类型转换:
枚举值可以隐式转换为整数,但最好避免,在需要明确类型的场合这样做。
- 范围:
枚举值在底层是整数,因此它们有范围限制(通常是
int
的范围)。
(4)示例
#include <stdio.h>
// 定义一个枚举类型 Color,包含几种颜色
enum Color
{
RED, // 枚举成员 RED
GREEN, // 枚举成员 GREEN
BLUE, // 枚举成员 BLUE
YELLOW = 66, // 显式赋值为 66 的枚举成员 YELLOW
PURPLE // 枚举成员 PURPLE,隐式赋值,其值将为 66 + 1
};
int main()
{
// 声明一个枚举类型的变量 favoriteColor,并初始化为 RED
enum Color favoriteColor = RED;
// 如果 favoriteColor 的值为 RED ,则打印信息
if (favoriteColor == RED)
{
printf("favorite color is Red.\n");
}
// 打印枚举值对应的整数值
// 枚举值可以隐式转换为整数,这里打印 favoriteColor 的整数值
printf("Enum value as integer: %d\n", favoriteColor);
// 整数也可以显式转换为枚举类型,但这样做是不安全的,除非确保整数值在枚举范围内
// 这里将整数 4显式转换为枚举类型,但这个值不在枚举定义的范围内,因此是未定义行为
enum Color anotherColor = (enum Color)4; // 这是一个未定义的枚举值
// 使用时要小心,因为这样的值可能超出枚举的定义范围
return 0;
}
- 输出结果:
总结
联合(union
):用于在同一内存位置存储不同类型的值,适用于节省内存的场景,但需要注意访问时的数据一致性。
枚举(enum
):用于定义一组命名的整数常量,使代码更加清晰和可读,适用于表示固定集合的值的场景。
END
每天都在学习的路上!
On The Way Of Learning