Learning C++ #13: Getting to Know Union Data Types

 

Understanding union data types in C++

After learning about Struct , next we will get acquainted with the Union data type.

What is union?

Why do we need a union?

How is it different from a struct?

..and how to use union?

Let's learn!

What is Union?

Union is a data type that contains a set of variables wrapped together and has the same memory address .

Union is actually similar to struct and class. However, they differ in the way they provide memory addresses.

Why do we need a union?

To answer this, we will use a case study.

For example, we are going to make a game, then want to save data on the weapons owned by the player.

Let's just say the player has two weapons, namely: a gun and a knife.

Then we can create a struct like this:

struct Senjata 
{
	string nama;
	int jumlah_peluru;
	int ketajaman;
};

Pay attention to the variables jumlah_peluruand ketajaman. This variable is required for each type of weapon.

Guns require jumlah_peluruand knives require ketajaman.

If the player only has a gun, that means the variable ketajamanwill be in vain. Vice versa.

So, so that it's not wasted, we have to store the variable jumlah_peluruin ketajaman one memory address.

We can do this with a union like this:

struct Senjata 
{
	string nama;
	union {
		int jumlah_peluru;
		int ketajaman;
	}
};

This way, variables jumlah_peluruand ketajamanwill use the same memory address. This will certainly be more efficient.

So why do we need union?

Union we need when we want to use one memory address for two or more variables.

How to Create a Union

We can create a union with keywords unionfollowed by the name of the union.

After that we use curly braces to define members and their data types.

define union

Some conditions for creating a Union in C++:

  • Union members can contain functions
  • Union members cannot use non-static or reference data types, for example objects. 1
  • If you want to use non-static members, you have to create a constructor and destructor.
  • Union is similar to a struct, member access is public.

Example:

union Product 
{
  char* name;
  unsigned int price;
  unsigned int stock;
  float weight;
};

Then how to use it:

// membaut variabel untuk union
Product p;

// mengisi data ke member union
p.name = "Pupuk NPK 1kg";
p.price = 200000;
p.stok = 999;

A variable pis a variable that contains a union and within it there are members that will use the same memory address.

We can also create a union without a name like this:

union 
{
  float x;
  float y;
};

..and we can also store this unnamed Union in a Struct:

Example:

struct Buku 
{
  char *title ;
  bool is_digital;
  union {
  	char *format;
    float weight;
  };
};

In the struct Bukuthere is uniona nameless struct containing variables formatand weight. These two variables will use the same memory address and can be directly accessed from the struct Buku.

Example:

// membuat variabel struct
Buku belajar_cpp;

// mengakses union di dalam struct
belajar_cpp.format = "PDF";

To understand better, let's try practicing.

Exercise: Using Union

After knowing how to define or create a union, it's time to try using it.

Create a new program with the name contoh_union.c, then fill in the code like this:

#include <iostream>
using namespace std;

// membuat struct yang berisi union
struct Notification
{
    enum { EMAIL, SMS } type;
    string title;
    string message;
    union
    {
        char* phone_number;
        char* email_address;
    };
};

int main()
{
    Notification sms =
    {
        .type = Notification::SMS,
        .title = "Greeting",
        .message = "Halo Selamat datang",
        .phone_number = "081234567890"
    };

    Notification email =
    {
        .type = Notification::EMAIL,
        .title = "Welcome",
        .message = "Selamat datang di aplikasi",
        .email_address = "mail@petanikode.com"
    };

    // show notification
    cout << "## 🔔 NOTIFICATION SMS ##\n";
    cout << "to: " << sms.phone_number << endl;
    cout << "message: " << sms.message << endl;

    cout << endl;

    cout << "## ✉ NOTIFICATION EMAIL ##\n";
    cout << "subject: " << email.title << endl;
    cout << "to: " << email.email_address << endl;
    cout << "message: " << email.message << endl;

    return 0;
}

After that, try compiling and running it.

So the result is:

union example

In this program, we create a notification system with two different types of notifications. There are notifications in the form of email and SMS.

Thanks to union we can determine the destination of sending notifications with different types, namely can phone_numberand email_address.

Difference between Union and Struct

Union is actually the same as the Struct data type. However, they differ in their memory allocation methods.

The struct allocates memory for each member at a different memory address.

Meanwhile, Union allocates memory at one memory address with the size taken from the size of the largest member.

Example:

struct Player 
{
  char *name; // address: 00000011
  unsigned int level; // address: 00000012
}

union Enemy 
{
  char *name; // 00000022
  unsigned int hp; // 00000022
}

Each member of the struct Playerwill use a different memory address. Meanwhile, union Enemyonly uses one memory address.

To make it clearer, let's try practice.

Latihan: Struct vs Union

Create a new program with the name union_vs_struct.cpp, then fill it with the following code:

#include <iostream>
#include <stdio.h>
using namespace std;

struct Player
{
    string name;
    unsigned int level;
};

union Enemy
{
    char *name;
    unsigned int hp;
};

int main()
{
    Player player1 =
    {
        .name = "Petani Kode",
        .level = 1
    };

    printf("Player  : %d  (address = %x)\n", sizeof(player1), &player1);
    printf(" - name : %d  (address = %x)\n", sizeof(player1.name), &player1.name);
    printf(" - level: %d  (address = %x)\n", sizeof(player1.level), &player1.level);


    union Enemy zombie;
    zombie.name = "Zombie 1";
    zombie.hp = 100;

    printf("Enemy   : %d  (address = %x)\n", sizeof(zombie), &zombie);
    printf(" - name : %d  (address = %x)\n", sizeof(zombie.name), &zombie.name);
    printf(" - Hp   : %d  (address = %x)\n", sizeof(zombie.hp), &zombie.hp);

    return 0;
}

After that, try compiling and running it.

So the result is:

union example

The memory size of the union Enemyis 8because it takes the size of the largest member, namely the size of name.

The memory address used by each member unionis the same. Unlike structs Playerwhere the addresses are different.

What is next?

We have learned and understood the union type in C. We don't always have to use union.

But..

In certain cases as exemplified above, we are advised to use union.

Next, please learn about pointers in C++.

Post a Comment

Previous Post Next Post