作者:旧梦拾遗186
相关链接:C语言自定义类型详解上:结构体
每日励志:
面对悬崖峭壁,一百年也看不出一条缝来,但用斧凿,得进一寸进一寸,得进一尺进一尺,不断积累,飞跃必来,突破随之。——华罗庚
前言:
由于篇幅较长小编将自定义类型 非为上下两篇来总结,本篇博客内容包括(枚举和联合体),上篇博客包含(结构体)可点击相关链接进入C语言自定义类型详解上:结构体
目录
一.枚举:
1.1枚举的基本概念
- 顾名思义枚举就是列举,把可能的取值列举出来。
例如在我们的生活中,周一到周日是有限的七天,可以一一列举。
1.2枚举的定义
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 Day { Mon, Tues, Wed, Thur, Fri, Sat, Sun }; int main() { return 0; }
以上就是枚举的定义。我们要补充的是,枚举的默认值从 0 开始,每往下走递增 1 。就好比上面这段代码,Mon 的值默认为 0 ,Tues 的值从 0 递增 1,为 1,Wed 为 2,Thur 为 3……
当然我们可以自定义,不从 0 开始:
#include<stdio.h> enum color { red, bule=80, green, brown, witle=90, yellow }; int main() { enum color c = red; printf("%d\n", green); printf("%d", yellow); return 0; }
bule的值赋值为80那么green的值就为81.
1.3枚举的使用
#include<stdio.h> enum color { red, bule=80, green, brown, witle=90, yellow }; int main() { enum color c = red; enum color c2 = 12; //此种写法是不推荐的,因为存在类型差异 return 0; }
只能拿枚举常量给枚举变量赋值,才不会出现类型的差异。
1.4枚举的优点
为什么使用枚举?我们可以使用 #define 定义常量,为什么非要使用枚举?枚举的优点:1. 增加代码的可读性和可维护性2. 和 #define 定义的标识符比较枚举有类型检查,更加严谨。3. 防止了命名污染(封装)4. 便于调试5. 使用方便,一次可以定义多个常量
二.联合体
2.1联合的基本概念
- 联合体也是一种特殊的自定义类型。
- 这种类型定义的变量也包含一系列成员,特征是这些成员共用一块空间
2.2联合类型的定义
联合也是一种特殊的自定义类型这种类型定义的变量也包含一系列的成员,特征是这些成员公用同一块空间(所以联合也叫共用体)。比如://联合类型的声明 union Un { char c; int i; }; //联合变量的定义 union Un un; //计算联合体变量的大小 printf("%d\n", sizeof(un));
2.3联合体的特点
联合的成员是共用同一块内存空间的,这样一个联合变量的大小,至少是最大成员的大小(因为联合至少得有能力保存最大的那个成员)。#include<stdio.h> union Un { int i; char c; }; int main() { union Un un; // 下面输出的结果是一样的吗? printf("%d\n", &(un.i)); printf("%d\n", &(un.c)); //下面输出的结果是什么? un.i = 0x11223344; un.c = 0x55; printf("%x\n", un.i); return 0; }
通过printf("%d\n", &(un.i)); printf("%d\n", &(un.c));可以看出联合体中两个变量占用同一块空间。通过un.i = 0x11223344; un.c = 0x55;printf("%x\n", un.i);可以看出,两个变量在同一块空间进行修改
2.4通过联合体判断大小端
方法一:
#include <stdio.h> int check_sys() { int a = 1; return *(char*)&a; } int main() { int ret = check_sys(); if (ret == 1) { printf("小端\n"); } else { printf("大端\n"); } return 0; }
方法二:
#include <stdio.h> int check_sys() { union Un { char c; int i; }u; u.i = 1; return u.c; } int main() { int ret = check_sys(); if (ret == 1) { printf("小端\n"); } else { printf("大端\n"); } return 0; }
2.5联合体大小计算
联合的大小至少是最大成员的大小。当最大成员大小不是最大对齐数的整数倍的时候,就要对齐到最大对齐数的整数倍。
例如:
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));
联合体union Un1中char类型的字节大小为1,机器的最大对齐数是8所以char类型的对齐数为1,同理int类型的对齐数为4,在最大对齐数为4,又因为char类型的数组开辟了5个字节的空间,小于最大对齐数的整数倍,要对齐导最大对齐数的整数倍即为8
三.结语:
以上是自定义类型的详解下半部分,通过两篇博客的学习我们对自定义类型有了更加深入的了解,认识了结构体、位段、枚举、联合。
每个人的成长都是能力和想要得到的东西,不断匹配的过程,当你的才华和欲望不匹配时,你就该静下心来学习了,如果小编的总结能对你有所帮助,希望小伙伴们三连加关注哦,你的支持是小编创作的最大动力。