連載

C#入門

第16回 列挙型の活用

(株)ピーデー
川俣 晶
2001/11/23


数値として使う列挙型

 すでに述べたとおり、列挙型の中身は数値である。実際に、個々の要素に対応する数値を確かめるには以下のように記述する。

 1: using System;
 2:
 3: namespace ConsoleApplication5
 4: {
 5:   enum Era
 6:   {
 7:     Meiji,
 8:     Taisho,
 9:     Showa,
10:     Heisei
11:   }
12:   class Class1
13:   {
14:     static void Main(string[] args)
15:     {
16:       Console.WriteLine( (int)Era.Meiji );
17:       Console.WriteLine( (int)Era.Taisho );
18:       Console.WriteLine( (int)Era.Showa );
19:       Console.WriteLine( (int)Era.Heisei );
20:     }
21:   }
22: }
列挙型を数値として使用したサンプル・プログラム5
列挙型の値を数値にキャストして表示する。

 これを実行すると以下のようになる。

サンプル・プログラム5の実行結果
最初の項目が0に割り当てられ、それ以降1ずつ値が増えているのが分かる。

 16〜19行目のように、列挙型の値は数値にキャストできる。何も指定しない場合、列挙型はint型の数値で内部処理されるので、int型へ問題なくキャストできる。結果を見て分かるとおり、特に何も指定しなければ、最初の項目が0に割り当てられ、それ以降1ずつ値が増えていく。

内部処理用の数値型の変更

 何も指定しなければ、列挙型はint型で内容を処理する。しかし、内容の処理に使われるデータ型は、必要なら指定して変更することもできる。例えばメモリの節約のために、より少ないビット数の数値型にすることもできるし、表現力を高めるために、より多くのビット数からなる数値型にすることもできる。符号付きと符号なしも選べる。以下は、それを記述してみたサンプル・ソースである。

 1: using System;
 2:
 3: namespace ConsoleApplication6
 4: {
 5:   enum Era : byte
 6:   {
 7:     Meiji,
 8:     Taisho,
 9:     Showa,
10:     Heisei
11:   }
12:   class Class1
13:   {
14:     static void Main(string[] args)
15:     {
16:       Console.WriteLine( (byte)Era.Meiji );
17:       Console.WriteLine( (byte)Era.Taisho );
18:       Console.WriteLine( (byte)Era.Showa );
19:       Console.WriteLine( (byte)Era.Heisei );
20:     }
21:   }
22: }
列挙型で使用される数値型を変更しているサンプル・プログラム6
列挙型の名前を書いた直後に使用したい数値型を記述する。

 これを実行すると以下のようになる。

サンプル・プログラム6の実行結果
内部処理で使用される型をbyte型に指定している。

 ここでのポイントは、5行目で、列挙型の名前を書いた直後に、コロン記号を置いて、その後に使用したい数値型を書くことである。これにより、Era型はbyte型の整数で内部処理されるようになる。

privateな列挙型

 列挙型の宣言には、クラスと同じように、privateなどのキーワードを付けて利用範囲を制限することができる。以下はそれを実際に記述した例である。

 1: using System;
 2:
 3: namespace ConsoleApplication7
 4: {
 5:   class Class2
 6:   {
 7:     private enum Era
 8:     {
 9:       Meiji,
10:       Taisho
11:     }
12:     public static void WriteMeiji()
13:     {
14:       Console.WriteLine( Class2.Era.Meiji );
15:     }
16:   }
17:   class Class1
18:   {
19:     enum Era
20:     {
21:       Showa,
22:       Heisei
23:     }
24:     static void Main(string[] args)
25:     {
26:       //Console.WriteLine( Class2.Era.Meiji );  //エラー 'ConsoleApplication7.Class2.Era' はアクセスできない保護レベルになっています。
27:         Class2.WriteMeiji();
28:         Console.WriteLine( Class1.Era.Showa );
29:     }
30:   }
31: }
列挙型にprivateを指定したサンプル・プログラム7
クラス外からアクセスするようなコードはコンパイル・エラーとなる。

 これを実行すると以下のようになる。

サンプル・プログラム7の実行結果
privateを付けた列挙型は、それを宣言したクラス内からのみ使用できる。

 ここでポイントになるのは、2つのEra型が定義されていることだ。1つは7〜11行目、もう1つは19〜23行目だ。このうち7〜11行目のEra型はClass2クラスの中で宣言され、privateキーワードが付いているので、クラス外からは利用できない。実際、26行目のようなコードを書くと、「エラー 'ConsoleApplication7.Class2.Era' はアクセスできない保護レベルになっています。」というエラーになり、コンパイルできない。しかし、14行目のように、同じクラス内からは問題なく利用することができる。

名前に任意の数値を与える

 すでに述べたように、列挙型の個々の要素には、何も指定しなければ、0から順番に1ずつ大きくなる値が割り当てられる。しかし必要なら、値を明示的に指定することで変更することができる。以下はそれを行った例である。

 1: using System;
 2:
 3: namespace ConsoleApplication8
 4: {
 5:   enum Sample
 6:   {
 7:     A,
 8:     B,
 9:     C = 10,
10:     D,
11:     E = B
12:   }
13:   class Class1
14:   {
15:     static void Main(string[] args)
16:     {
17:       Console.WriteLine( (int)Sample.A );
18:       Console.WriteLine( (int)Sample.B );
19:       Console.WriteLine( (int)Sample.C );
20:       Console.WriteLine( (int)Sample.D );
21:       Console.WriteLine( (int)Sample.E );
22:     }
23:   }
24: }
列挙型の要素に任意の数値を割り当てたサンプル・プログラム8
列挙型であるSample型の要素CおよびEに値を割り当てている。

 これを実行すると以下のようになる。

サンプル・プログラム8の実行結果
“10”を割り当てた“C”の次の要素“D”は“11”となっている。

 実行結果を見て分かるとおり、何も指定していない7〜8行目のAとBは0と1になる。しかし、9行目のCは、明示的に“C = 10”としているので、10という値を持つ。次の10行目のDは、Cの次なので、10の次つまり11になる。最後の11行目のEは、“E = B”として、Bと同じとしているため、Bの値、つまり1になる。

 列挙型の値を変更するのは、数値に何か特別な意味があって、それと一致させたい場合である。逆に数値に特別な意味がないのに、数値を明示的に指定すると予期せぬトラブルが起こる場合があるので、必要性を見極めてから利用しよう。


 INDEX
  第16回 列挙型の活用
    1.列挙型とは何か
  2.数値として使う列挙型
    3.数値指定時のトラブル例
    4.列挙型のすべての数値を得る
 
「C#入門」


Insider.NET フォーラム 新着記事
  • 第2回 簡潔なコーディングのために (2017/7/26)
     ラムダ式で記述できるメンバの増加、throw式、out変数、タプルなど、C# 7には以前よりもコードを簡潔に記述できるような機能が導入されている
  • 第1回 Visual Studio Codeデバッグの基礎知識 (2017/7/21)
     Node.jsプログラムをデバッグしながら、Visual Studio Codeに統合されているデバッグ機能の基本の「キ」をマスターしよう
  • 第1回 明瞭なコーディングのために (2017/7/19)
     C# 7で追加された新機能の中から、「数値リテラル構文の改善」と「ローカル関数」を紹介する。これらは分かりやすいコードを記述するのに使える
  • Presentation Translator (2017/7/18)
     Presentation TranslatorはPowerPoint用のアドイン。プレゼンテーション時の字幕の付加や、多言語での質疑応答、スライドの翻訳を行える
@ITメールマガジン 新着情報やスタッフのコラムがメールで届きます(無料)

注目のテーマ

Insider.NET 記事ランキング

本日 月間