C语言联合和枚举讲解

目录

 联合体的大小

 联合体如何省空间

巧用联合体 

联合判断大小端(惊为天人,大佬写的,我借鉴) 

 枚举

枚举类型的使用 


首先我们先看一下菜鸟教程中的对C语言联合体的说明

 联合体的大小

 

#include <stdio.h>
union u
{
	char c;
	int u;
};

int main()
{
	union u n;
	printf("%zd\n", sizeof(n));
	return 0;;
}

 这里为什么是4呢?

 

 这里已经给了我们答案,为了更加直观,我们取地址打印一下

 

#include <stdio.h>
union u
{
	char c;
	int u;
};

int main()
{
	union u n;
	printf("%p\n", &n);
	printf("%p\n", &n.c);
	printf("%p\n", &n.u);


	return 0;;
}

 

所以联合体也叫共用体

我们在这解释一下联合体大小应该怎样计算

1.联合体的大小至少是最大成员的大小。

2.当最大成员大小不是最大对齐数的整数倍的时候,就要对齐到最大对齐数的整数倍

上述的计算方法的第二点我们写个代码再解释一下

#include <stdio.h>
union Un1
{
	char c[5];//5
	//注意此时如果是数组的话要按照数据所属的类型大小来计算,char类型就是1
	//1  8  1
	int i;//4 8  4
};

int main()
{
	printf("%zd\n", sizeof(union Un1));
	return 0;
}

 

 有了这样代码中的注释我们或许就能理解结构体大大小是如何计算的。

 联合体如何省空间

 

对于商品来说,他们具有相同的价格类型,产地信息,但有的商品具有的信息别的商品没有,我们完全可以写出一个结构体包含这这个他们的公共属性和各自具有的属性,但这样的话太浪费空间了,比如说你此时就想描述一件商品,那你还需要再描述其他两件不必要的特殊属性了。

因此我们的解决办法是现将公共属性单独写出来,剩余属于各个商品本身的特殊属性我们就用联合体联合起来,这样做的话,就节省了空间。

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[20];//设计
			int colors;//颜色
			int sizes;//尺寸
		}shirt;
	}item; 
};

这样写就很节省空间了。

巧用联合体 

 我们来看一个比较厉害的代码:(一个int类型,一次取出一个字节)

union U
{
	int n;//4
	struct S
	{
		char c1;
		char c2;
		char c3;
		char c4;
	}s;//4
};

int main()
{
	union U u = { 0 };
	u.n = 0x11223344;
	printf("%x %x %x %x\n", u.s.c1, u.s.c2, u.s.c3, u.s.c4);
	return 0;
}

联合判断大小端(惊为天人,大佬写的,我借鉴) 

 

int check()
{
	union
	{
		char c;
		int i;
	}u;
	u.i = 1;
	return u.c;
}

int main()
{
	int ret = check();
	if (ret == 1)
		printf("小端\n");
	else
		printf("大端\n");
	return 0;
}

 

 此时char不用进行强制转换,因为字符型的ascll类型也是整型

 枚举

enum day
{
	Mon,
	Tues,
	Web,
	Thur,
	Fri,
	Sat,
	Sun
};

int main()
{
	printf("%d\n", Mon);
	printf("%d\n", Tues);
	printf("%d\n",Web);
	printf("%d\n", Thur);
	printf("%d\n", Fri);
	printf("%d\n", Sat);
	printf("%d\n", Sun);

	return 0;
}

 

枚举类型默认值为0

还有我们可以对我们枚举中的数据进行初始化,但他们都是常量,因此在主函数中,我们要再想要改变他们的值,那编译器就会报错。我们对其进行初始化我们进行观察一下

 

 

 我们再来看一下我们在主函数中更改他的值进行报错的情况:

 

 

因此在使用时我们应该注意。

枚举类型的变量必须是属于枚举类型的,我们对此进行展示

enum day
{
	Mon=2,
	Tues=4,
	Web=5,
	Thur=6,
	Fri=9,
	Sat=11,
	Sun=19
};

int main()
{
	enum day s = Mon;
	s = Fri;
	return 0;
}

 

枚举的优点:

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

枚举类型的使用 

enum day
{
	Mon=2,
	Tues=4,
	Web=5,
	Thur=6,
	Fri=9,
	Sat=11,
	Sun=19
};

int main()
{
	enum day s = Mon;//使用枚举常量给枚举变量赋值
	
	return 0;
}

 

C语言中可以拿整数给枚举变量赋值,但C++中不行。

若有收获,就点个赞吧!

  • 12
    点赞
  • 7
    收藏
    觉得还不错? 一键收藏
  • 6
    评论

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

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

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

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

余额充值