C言語

列挙型(enum)の基本

C言語では、数字に名前をつけてわかりやすくしたいときに「列挙型(れっきょがた)」という仕組みを使うことができます。
今回は、この列挙型(enum)の基本的な使い方について解説します。

列挙型とは?

列挙型(enumとは、グルーピングしている選択肢に名前をつけてまとめるための仕組みです。

たとえば、信号の色をプログラムで表したいとします。
#defineとマクロ関数の基本」では、#defineを使えば、信号の色を定数名で表すことができました。

#define RED   0
#define YELLOW 1
#define GREEN  2

この定数名を使う場合は、

if (signal == RED)

このように書けるので、数字のまま比較するよりも分かりやすいです。

ただ、この方法だと、いくつかの欠点があります。

#defineの欠点

  • どこにでも書けるため、定義がバラバラになりやすい
    信号の色なので、この3つは関連している名前です。
    ただ、#defineでは、個々に定義するので、関連していることがわかりにくくなります。
  • 型がないので、まちがった使い方をしても気づきにくい
    これは、ピンとこないと思いますので、列挙型(enum)を説明した後、紹介します。
  • 値を必ずつける必要があるため、意味がなくても数字を決めなければならない
    信号機の色の値に意味はありません。3つの違いを区別するために適当に付けた値です。

列挙型(enum)の宣言

列挙型は、どのような型であるかを宣言する必要があります。

列挙型の宣言の構文は次の通りです。

enum 列挙型名 {
  定数名1,
  定数名2,
  定数名3,
  ...
};

enum :列挙型を作るというキーワード
列挙型名:任意の名前(型の名前を決めることができる)
定数名(識別子):#defineの定数名に相当する(RED、YELLOWなど)
最後にセミコロン( ; )を付けて、宣言の終わりを表します。

#defineで定義した信号の色を表した列挙型の例は次の通りです。

enum Signal {
  RED,
  YELLOW,
  GREEN
};

この宣言で、「Signal」という型(グループ)の中に、「RED」「YELLOW」「GREEN」という定数ができました。

列挙型(enum)の使い方

作った列挙型は、変数として使うことができます。
次に、実際に列挙型を使った例を紹介します。

#include <stdio.h>

enum Signal {
  RED,
  YELLOW,
  GREEN
};

int main(void)
{
  enum Signal signal;  // Signal型の変数を作る
  signal = GREEN;      // GREENを代入

  if (signal == RED) {
    printf("止まってください。\n");
  } else if (signal == YELLOW) {
    printf("注意して進んでください。\n");
  } else {
    printf("進んでOKです。\n");
  }

  return 0;
}

プログラムの解説

enum Signal { RED, YELLOW, GREEN }; にて、列挙型を定義します。
Signalという名前の列挙型を作って、「RED」「YELLOW」「GREEN 」の3つの定数を定義します。

enum Signal signal; では、「Signal」の型(列挙型)の変数 signal を定義します。
この変数 signal には、「RED」「YELLOW」「GREEN」のいずれかの値が入ります。

signal = GREEN; では、変数 signalGREEN を代入しています。
今は信号が「青(緑)」の状態だということです。

if (signal == RED) は、もし、信号が赤なら、「止まってください。」と表示します。
同じように黄や緑の場合もそれぞれのメッセージを表示します。

列挙型を使うと、「0」や「1」といった数字ではなく、
RED や GREEN などの“意味のある名前”で条件分岐ができるため、読みやすくなります。
プログラムを読む人にも「この変数は信号の状態を表しているんだな」とすぐ伝わります。

列挙型の定数の値は数字

列挙型の中では、何も値を指定しないと、次のように自動で、0 から順に番号がつきます。
 RED:0
 YELLOW:1
 GREEN:2
つまり、内部的には「RED=0、YELLOW=1、GREEN=2」として扱われます。

ですが、プログラムを書くときは数字を意識する必要はありません。
名前(REDなど)を使えばOKです。

列挙型の定数の値をかえることができる

必要であれば、最初の値を指定することもできます。

enum Signal {
  RED = 10,
  YELLOW,
  GREEN
};

このように書くと、
 RED:10
 YELLOW:11
 GREEN:12

enum Signal {
  RED = 10,
  YELLOW =20,
  GREEN
};

このように書くと、
 RED:10
 YELLOW:20
 GREEN:21

#defineとの違い

列挙型は、#define と似ています。
どちらも「定数に名前をつける」ために使います。
ただし、次のような違いがあります。

比較項目#defineenum
定義方法ひとつずつ定義するひとまとめで定義する
グループ化できないできる(型としてまとまる)
値の指定必ず必要任意(明記しないと、自動で0,1,2...)

まとめ

  • enum は「決まった種類の定数をまとめる」ための仕組み。
    構文は
    enum 型名 { 定数1, 定数2, ... };
    の形で書く。
  • 値は自動で0から順番に割り当てられる。
  • 名前を使って分かりやすく書ける。
  • 値に意味がないものをまとめたいときに便利。

-C言語