Cprogramming 简明教程

Unions in C

Unions in C

union 是 C 语言中提供的特殊数据类型,允许在同一内存位置存储不同的 data types 。你可以定义一个有多个成员的联合,但任何给定时间的只有一个成员可以包含值。联合提供了对使用同一内存位置进行多种用途的有效方式。

A union is a special data type available in C that allows to store different data types in the same memory location. You can define a union with many members, but only one member can contain a value at any given time. Unions provide an efficient way of using the same memory location for multiple purpose.

联合的所有成员共享同一内存位置。因此,如果我们需要对两个或更多成员使用同一内存位置,那么联合是对此而言的最佳数据类型。最大的联合成员定义联合的大小。

All the members of a union share the same memory location. Therefore, if we need to use the same memory location for two or more members, then union is the best data type for that. The largest union member defines the size of the union.

Defining a Union

联合变量的创建方式与结构变量的创建方式相同。关键字 union 用于在 C 语言中定义联合。

Union variables are created in same manner as structure variables. The keyword union is used to define unions in C language.

Syntax

以下是 C 语言中定义 union 的语法:

Here is the syntax to define a union in C language −

union [union tag]{
   member definition;
   member definition;
   ...
   member definition;
} [one or more union variables];

“联合标记”是可选的,每个成员定义都是一个常量变量定义,例如“int i;”或“float f;”或任何其他有效的变量定义。

The "union tag" is optional and each member definition is a normal variable definition, such as "int i;" or "float f;" or any other valid variable definition.

在联合定义的末尾,在最终分号之前,可以指定一个或多个联合变量。

At the end of the union’s definition, before the final semicolon, you can specify one or more union variables.

Accessing the Union Members

要访问联合的任何成员,我们需要使用成员访问运算符 (.)。成员访问运算符编码为联合变量名和我们希望访问的联合成员之间的句点。你应该使用关键字联合来定义联合类型的变量。

To access any member of a union, we use the member access operator (.). The member access operator is coded as a period between the union variable name and the union member that we wish to access. You would use the keyword union to define variables of union type.

Syntax

以下是访问 C 语言中联合成员的语法 −

Here is the syntax to access the members of a union in C language −

union_name.member_name;

Initialization of Union Members

你可以通过使用赋值 (=) 运算符将值赋值给它们,初始化联合的成员。

You can initialize the members of the union by assigning the value to them using the assignment (=) operator.

Syntax

以下是初始化联合成员的语法 −

Here is the syntax to initialize members of union −

union_variable.member_name = value;

Example

以下代码语句显示了联合“数据”的成员“i”的初始化 −

The following code statement shows to initialization of the member "i" of union "data" −

data.i = 10;

Examples of Union

Example 1

以下示例展示了如何在程序中使用联合 −

The following example shows how to use unions in a program −

#include <stdio.h>
#include <string.h>

union Data{
   int i;
   float f;
   char str[20];
};

int main(){
   union Data data;

   data.i = 10;
   data.f = 220.5;
   strcpy(data.str, "C Programming");

   printf("data.i: %d \n", data.i);
   printf("data.f: %f \n", data.f);
   printf("data.str: %s \n", data.str);
   return 0;
}

编译并执行上述代码后,将产生以下结果 −

When the above code is compiled and executed, it produces the following result −

data.i: 1917853763
data.f: 4122360580327794860452759994368.000000
data.str: C Programming

在此,我们可以看到 if (联合的成员) 的值显示 garbage values ,因为分配给变量的最终值占据了内存位置,这就是 str 成员值能够很好地打印出来的原因。

Here, we can see that the values of i and f (members of the union) show garbage values because the final value assigned to the variable has occupied the memory location and this is the reason that the value of str member is getting printed very well.

Example 2

现在,让我们再次看一下同一个示例,其中我们将一次使用一个变量,这是拥有联合的主要目的 −

Now let’s look at the same example once again where we will use one variable at a time which is the main purpose of having unions −

#include <stdio.h>
#include <string.h>

union Data{
   int i;
   float f;
   char str[20];
};

int main(){

   union Data data;

   data.i = 10;
   printf("data.i: %d \n", data.i);

   data.f = 220.5;
   printf("data.f: %f \n", data.f);

   strcpy(data.str, "C Programming");
   printf("data.str: %s \n", data.str);
   return 0;
}

编译并执行上述代码后,将产生以下结果 −

When the above code is compiled and executed, it produces the following result −

data.i: 10
data.f: 220.500000
data.str: C Programming

在此,所有联合成员的值都能很好地打印出来,因为一次只使用一个成员。

Here, the values of all the Union members are getting printed very well because one member is being used at a time.

Size of a Union

联合的大小是其最大成员的大小。例如,如果一个联合包含 charint 类型的两个成员。在这种情况下,联合的大小将是 int 的大小,因为 int 是最大的成员。

The size of a union is the size of its largest member. For example, if a union contains two members of char and int types. In that case, the size of the union will be the size of int because int is the largest member.

你可以使用 sizeof() operator 来获取联合的大小。

You can use the sizeof() operator to get the size of a union.

Example

在以下示例中,我们正在打印一个联合的大小 −

In the following example, we are printing the size of a union −

#include <stdio.h>

// Define a union
union Data {
   int a;
   float b;
   char c[20];
};

int main() {
   union Data data;

   // Printing the size of the each member of union
   printf("Size of a: %lu bytes\n", sizeof(data.a));
   printf("Size of b: %lu bytes\n", sizeof(data.b));
   printf("Size of c: %lu bytes\n", sizeof(data.c));

   // Printing the size of the union
   printf("Size of union: %lu bytes\n", sizeof(data));

   return 0;
}

当你编译并执行该代码时,它将生成以下输出 −

When you compile and execute the code, it will produce the following output −

Size of a: 4 bytes
Size of b: 4 bytes
Size of c: 20 bytes
Size of union: 20 bytes

Difference between Structure and Union

structures 和联合都是 C 编程中的复合数据类型。结构和联合之间最显著的区别是它们存储数据的方式。结构将每个成员存储在单独的内存位置中,而联合将所有成员存储在同一个内存位置中。

Both structures and unions are composite data types in C programming. The most significant difference between a structure and a union is the way they store their data. A structure stores each member in separate memory locations, whereas a union stores all its members in the same memory location.

以下是名为 myunion 的联合类型的定义 −

Here is a definition of union type called myunion

union myunion{
   int a;
   double b;
   char c;
};

联合的定义类似于结构的定义。“struct type mystruct”的定义,其元素相同,如下所示 −

The definition of a union is similar to the definition of a structure. A definition of "struct type mystruct" with the same elements looks like this −

struct mystruct{
   int a;
   double b;
   char c;
};

结构和联合之间的主要区别是变量的大小。编译器将内存分配给结构变量,以便能够为所有元素存储值。在 mystruct 中,有三个元素 − 一个 int、一个 double 和一个 char,需要 13 个字节 (4 + 8 + 1)。因此, sizeof(struct mystruct) 返回 13。

The main difference between a struct and a union is the size of the variables. The compiler allocates the memory to a struct variable, to be able to store the values for all the elements. In mystruct, there are three elements − an int, a double, and char, requiring 13 bytes (4 + 8 + 1). Hence, sizeof(struct mystruct) returns 13.

另一方面,对于联合类型变量,编译器开辟一块大小足以容纳字节大小最大的元素的内存块。 myunion 具有 int、double 和 char 元素。在三个元素中,double 变量的大小最大,即为 8。因此, sizeof(union myunion) 返回 8。

On the other hand, for a union type variable, the compiler allocates a chunk of memory of the size enough to accommodate the element of the largest byte size. The myunion type has an int, a double and a char element. Out of the three elements, the size of the double variable is the largest, i.e., 8. Hence, sizeof(union myunion) returns 8.

另一个需要考虑的问题是联合变量只能包含其一个元素的值。当为一个元素分配值时,其他元素是未定义的。如果您尝试使用其他元素,将导致一些内存垃圾。

Another point to take into consideration is that a union variable can hold the value of only one its elements. When you assign value to one element, the other elements are undefined. If you try to use the other elements, it will result in some garbage.

Example 1: Memory Occupied by a Union

在以下代码中,我们定义了一个名为 Data 的联合类型,其包含三个成员 ifstrData 类型的变量可以存储整数、浮点数或一系列字符。这意味着可以将一个变量(即相同存储器位置)用于存储多种类型的数据。您可以根据自己的需求在联合中使用任何内置或用户定义的数据类型。

In the code below, we define a union type called Data having three members i, f, and str. A variable of type Data can store an integer, a floating point number, or a string of characters. It means a single variable, i.e., the same memory location, can be used to store multiple types of data. You can use any built-in or user-defined data types inside a union, as per your requirement.

联合占用的内存将足够存储联合中最大的成员。例如,在上述示例中, Data 将占用 20 字节的存储空间,因为这是字符串可以占用的最大空间。

The memory occupied by a union will be large enough to hold the largest member of the union. For example, in the above example, Data will occupy 20 bytes of memory space because this is the maximum space which can be occupied by a character string.

以下示例显示了上一个联合占据的总内存大小 −

The following example displays the total memory size occupied by the above union −

#include <stdio.h>
#include <string.h>

union Data{
   int i;
   float f;
   char str[20];
};

int main(){
   union Data data;
   printf("Memory occupied by Union Data: %d \n", sizeof(data));
   return 0;
}

当你编译并执行该代码时,它将生成以下输出 −

When you compile and execute the code, it will produce the following output −

Memory occupied by Union Data: 20

Example 2: Memory Occupied by a Structure

现在,让我们创建一个具有相同元素的结构并检查它在内存中占用了多少空间。

Now, let’s create a structure with the same elements and check how much space it occupies in the memory.

#include <stdio.h>
#include <string.h>

struct Data{
   int i;
   float f;
   char str[20];
};

int main(){
   struct Data data;
   printf("Memory occupied by Struct Data: %d \n", sizeof(data));
   return 0;
}

此结构将占用 28 个字节 (4 + 4 + 20)。运行代码并检查其输出 −

This stucture will occupy 28 bytes (4 + 4 + 20). Run the code and check its output −

Memory occupied by Struct Data: 28