C语言之共用体Union

还有一种数据类型结构与结构体很相似,叫做共用体。接下来,就带大家看一看共用体Union的一些知识,以及两者之间的区别,帮助大家更好地理解二者的概念。

什么是共用体?

有时需要一种数据结构,不同的场合表示不同的数据类型。比如,如果只用一种数据结构表示学生的“成绩”,这种结构就需要有时是整数(80、90),有时是字符('A'、'B'),有时是浮点数(80.5、60.5)

C语言提供了共用体类型(Union 结构),用来自定义可以灵活变更的数据结构。它内部可以包含各种属性,但同一时间只能有一个属性,因为所有属性都保存在同一个内存地址,后面写入的属性会覆盖前面的属性。这样做的最大好处是节省空间。

“共用体”与“结构体”的定义形式相似,但它们的含义是不同的。 

结构体变量所占内存长度,可以认为是各成员占的内存长度的叠加;每个成员分别占有其自己的内存单元。共用体变量所占的内存长度等于最长的成员的长度;几个成员共用一个内存区。

共用体的声明

格式:

union 共用体类型名称
{
    数据类型 成员名1;
    数据类型 成员名2;
    …
    数据类型 成员名n;
};

如:

union data
{
    short m;
    float x;
    char c;
};

上例中,union命令定义了一个包含三个属性的数据类型data。虽然包含三个属性,但是同一时间只能取到一个属性。最后赋值的属性,就是可以取到值的那个属性。

共用体变量的声明同样有三种方式:

  1. 方式1:先定义共用体类型,再定义共用体变量
  2. 方式2:定义共用体类型的同时定义共用体变量
  3. 方式3:在定义时也可以不给出共用体名

共用体内存结构分析 

以上面例子中定义的共用体变量data为例,它由3个成员组成,分别是m、x和c,系统会按照最长的成员为它分配内存,由于成员x的长度最长,它占4个字节,所以共用体变量data的内存空间也为4个字节。

共用体成员的获取与赋值 

同结构体一样,共用体也使用点号 获取单个成员,可以进行赋值和取值。

  1. 方式1:union data a;  a.c = 4;
  2. 方式2:声明共用体变量的同时,给任一成员赋值  union data a = {.c = 4};
  3. 方式3:声明共用体变量的同时,给首成员赋值   union data a = {8};

注意:方式3不指定成员名,所以只能为第一个成员进行赋值。

练习案例

现有一张关于学生信息和教师信息的表格。学生信息包括姓名、编号、性别、职业、 分数,教师的信息包括姓名、编号、性别、职业、教学科目:可以参考下面的表格。利用共用体,只使用一个结构体保存每个人的信息。

Name

Num

Sex

Profession

Score / Course

孙二娘

501

女(f)

学生(s)

89.5

吴用

1011

男(m)

老师(t)

math

顾大嫂

109

女(f)

老师(t)

English

林冲

982

男(m)

学生(s)

95.0

#include <stdio.h>
#define TOTAL 2 // 人员总数

// 定义了一个结构体 Person
struct Person
{
    char name[20];   // name
    int num;         // 编号
    char sex;        // 性别 f => 女 m=>男
    char profession; // 职业 s=>学生 t=>老师
    union
    {
        float score;
        char course[20];
    } sc; // sc 是一个共用体变量
};

int main()
{
    int i;
    struct Person persons[TOTAL]; // 定义了一个结构体数组

    // 输入人员信息
    for (i = 0; i < TOTAL; i++)
    {
        printf("Input info: ");
        scanf("%s %d %c %c", persons[i].name, &(persons[i].num), &(persons[i].sex), &(persons[i].profession));

        if (persons[i].profession == 's')
        { // 如果是学生
            printf("请输入该学生成绩:");
            scanf("%f", &persons[i].sc.score);
        }
        else
        { // 如果是老师
            printf("请输入该老师课程:");
            scanf("%s", persons[i].sc.course);
        }
        fflush(stdin); // 刷新
    }

    // 输出人员信息
    printf("\nName\t\tNum\tSex\tProfession\tScore / Course\n");

    for (i = 0; i < TOTAL; i++)
    {
        if (persons[i].profession == 's')
        { // 如果是学生
            printf("%s\t\t%d\t%c\t%c\t\t%f\n", persons[i].name, persons[i].num, persons[i].sex, persons[i].profession, persons[i].sc.score);
        }
        else
        { // 如果是老师
            printf("%s\t\t%d\t%c\t%c\t\t%s\n", persons[i].name, persons[i].num, persons[i].sex, persons[i].profession, persons[i].sc.course);
        }
    }

    return 0;
}

通过这个例子,大家对C语言中的共用体掌握的怎么样了呢,欢迎大家交流讨论。

评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

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

抵扣说明:

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

余额充值