列挙体の値を文字列に変換するには、ToStringメソッドを使うのが簡単だが、任意の文字列に変換するには変換テーブルを使用する。また、処理を拡張メソッドに切り分けてもよい。
列挙体(または列挙型)の値、すなわち列挙値を文字列に変換したいことがある。列挙子(あるいは列挙メンバー)の名前に変換するなら簡単だが、(列挙子と対応付けられた)任意の文字列に変換するにはちょっと手間が掛かる。本稿では、それらの方法を解説する。
なお、列挙体の基本となるEnumクラス(System名前空間)は.NET Frameworkの最初からあるものだが、本稿はそれ以降の内容も含んでいる。サンプルコードをそのまま試すには、Visual Studio 2015(またはそれ以降)が必要である。
列挙子の名前に変換するなら、そのToStringメソッドを使えばよい。列挙子と対応付けた任意の文字列に変換するには、Dictionaryクラス(System.Collections.Generic名前空間)を利用した変換テーブルを用意しておく(次のコード)。
なお、特別な場合には、Dictionaryクラスの代わりに文字列の配列を使える(後述)。また、変換テーブル/配列の参照をする処理は、拡張メソッドにしておくとコードが分かりやすくなる(後述)。
// 列挙体の定義
enum e { a, b, c };
……省略……
var e1 = e.a;
// 列挙子の名前「a」を得る
string memberName = e1.ToString(); // ⇒ a
// 変換テーブルを使って対応する文字列を得る
var table = new Dictionary<e, string>
{ { e.a, "A" }, { e.b, "B" }, { e.c, "C" } };
string relatedName = table[e1]; // ⇒ A
' 列挙体の定義
Enum e
a
b
c
End Enum
……省略……
Dim e1 = e.a
' 列挙子の名前「a」を得る
Dim memberName As String = e1.ToString() ' ⇒ a
' 変換テーブルを使って対応する文字列を得る
Dim table = New Dictionary(Of e, String) _
From {{e.a, "A"}, {e.b, "B"}, {e.c, "C"}}
Dim relatedName As String = table(e1) ' ⇒ A
列挙値のToStringメソッドで、その列挙値に割り当てられている列挙子の名前が得られる。また、EnumクラスのGetNamesメソッドを使うと、全ての列挙子の名前を得ることもできる。次のコードにコンソールアプリの例を示す。
using System;
using static System.Console;
public enum JapaneseEraName1 { 明治 = 1, 大正, 昭和, 平成, }
class Program
{
static void Main(string[] args)
{
var era = JapaneseEraName1.平成;
string eraName = era.ToString();
WriteLine(eraName);
// 出力:平成
// 全ての名前を得る
string[] eraNames = Enum.GetNames(typeof(JapaneseEraName1));
WriteLine(string.Join(", ", eraNames));
// 出力:明治, 大正, 昭和, 平成
#if DEBUG
ReadKey();
#endif
}
}
Imports System.Console
Public Enum JapaneseEraName1
明治 = 1
大正
昭和
平成
End Enum
Module Module1
Sub Main()
Dim era = JapaneseEraName1.平成
Dim eraName As String = era.ToString()
WriteLine(eraName)
' 出力:平成
' 全ての名前を得る
Dim eraNames As String() = [Enum].GetNames(GetType(JapaneseEraName1))
WriteLine(String.Join(", ", eraNames))
' 出力:明治, 大正, 昭和, 平成
#If DEBUG Then
ReadKey()
#End If
End Sub
End Module
EnumクラスのToStringメソッドで得られる列挙子の名前とは違う文字列を得たい場合は、変換テーブルを参照する方法が基本になる。例えば、元号の正式名称と略称を得るには次のコードのようにする。なお、コードの中で略称の一覧も取得しているが、汎用的な記述はこのように面倒なものになる。
public enum JapaneseEraName2
{
Meiji=1868, Taisho=1912, Showa=1926, Heisei=1989,
}
……省略……
// JapaneseEraName2の値を元号の正式名称へ変換するためのテーブル
// (冒頭に「using System.Collections.Generic;」が必要)
static Dictionary<JapaneseEraName2, string> EraFullNames2
= new Dictionary<JapaneseEraName2, string>
{
{JapaneseEraName2.Meiji, "明治"},
{JapaneseEraName2.Taisho, "大正"},
{JapaneseEraName2.Showa, "昭和"},
{JapaneseEraName2.Heisei, "平成"},
};
// JapaneseEraName2の値を元号の略称へ変換するためのテーブル
static Dictionary<JapaneseEraName2, string> EraShortNames2
= new Dictionary<JapaneseEraName2, string>
{
{JapaneseEraName2.Meiji, "M"},
{JapaneseEraName2.Taisho, "T"},
{JapaneseEraName2.Showa, "S"},
{JapaneseEraName2.Heisei, "H"},
};
……省略……
var era = JapaneseEraName2.Heisei;
string eraFullName = EraFullNames2[era];
string eraShortName = EraShortNames2[era];
WriteLine($"{eraFullName}({eraShortName})");
// 出力:平成(H)
// 全ての略称を得る(冒頭に「using System.Linq;」が必要)
IEnumerable<string> shortNames
= Enum.GetValues(typeof(JapaneseEraName2))
.Cast<JapaneseEraName2>().Select(e => EraShortNames2[e]);
WriteLine(string.Join(", ", shortNames));
// 出力:M, T, S, H
Public Enum JapaneseEraName2
Meiji = 1868
Taisho = 1912
Showa = 1926
Heisei = 1989
End Enum
……省略……
' JapaneseEraName2の値を元号の正式名称へ変換するためのテーブル
Private EraFullNames2 As New Dictionary(Of JapaneseEraName2, String) _
From
{
{JapaneseEraName2.Meiji, "明治"},
{JapaneseEraName2.Taisho, "大正"},
{JapaneseEraName2.Showa, "昭和"},
{JapaneseEraName2.Heisei, "平成"}
}
' JapaneseEraName2の値を元号の略称へ変換するためのテーブル
Private EraShortNames2 As New Dictionary(Of JapaneseEraName2, String) _
From
{
{JapaneseEraName2.Meiji, "M"},
{JapaneseEraName2.Taisho, "T"},
{JapaneseEraName2.Showa, "S"},
{JapaneseEraName2.Heisei, "H"}
}
……省略……
Dim era = JapaneseEraName2.Heisei
Dim eraFullName As String = EraFullNames2(era)
Dim eraShortName As String = EraShortNames2(era)
WriteLine($"{eraFullName}({eraShortName})")
' 出力:平成(H)
' 全ての略称を得る
Dim shortNames As IEnumerable(Of String) _
= [Enum].GetValues(GetType(JapaneseEraName2)) _
.Cast(Of JapaneseEraName2)() _
.Select(Function(e) EraShortNames2(e))
WriteLine(String.Join(", ", shortNames))
' 出力:M, T, S, H
変換テーブルを参照する処理を拡張メソッドにしておくと、コードが分かりやすくなる(次のコード)。
// 列挙体JapaneseEraName2の定義は前のサンプルコードと同じなので省略
public static class JapaneseEraName2Extension
{
// JapaneseEraName2の値を元号の正式名称へ変換するためのテーブル
static Dictionary<JapaneseEraName2, string> EraFullNames2
= new Dictionary<JapaneseEraName2, string>
{
{JapaneseEraName2.Meiji, "明治"},
{JapaneseEraName2.Taisho, "大正"},
{JapaneseEraName2.Showa, "昭和"},
{JapaneseEraName2.Heisei, "平成"},
};
// JapaneseEraName2の値を元号の正式名称へ変換する拡張メソッド
public static string ToFullName(this JapaneseEraName2 era)
=> EraFullNames2[era];
// JapaneseEraName2の値を元号の略称へ変換するためのテーブル
static Dictionary<JapaneseEraName2, string> EraShortNames2
= new Dictionary<JapaneseEraName2, string>
{
{JapaneseEraName2.Meiji, "M"},
{JapaneseEraName2.Taisho, "T"},
{JapaneseEraName2.Showa, "S"},
{JapaneseEraName2.Heisei, "H"},
};
// JapaneseEraName2の値を元号の略称へ変換する拡張メソッド
public static string ToShortName(this JapaneseEraName2 era)
=> EraShortNames2[era];
}
……省略……
var era = JapaneseEraName2.Heisei;
string eraFullName = era.ToFullName();
string eraShortName = era.ToShortName();
WriteLine($"{eraFullName}({eraShortName})");
// 出力:平成(H)
' 列挙体JapaneseEraName2の定義は前のサンプルコードと同じなので省略
Public Module JapaneseEraName2Extension
' JapaneseEraName2の値を元号の正式名称へ変換するためのテーブル
Private EraFullNames2 As New Dictionary(Of JapaneseEraName2, String) _
From
{
{JapaneseEraName2.Meiji, "明治"},
{JapaneseEraName2.Taisho, "大正"},
{JapaneseEraName2.Showa, "昭和"},
{JapaneseEraName2.Heisei, "平成"}
}
' JapaneseEraName2の値を元号の正式名称へ変換する拡張メソッド
<System.Runtime.CompilerServices.Extension()>
Public Function ToFullName(era As JapaneseEraName2) As String
Return EraFullNames2(era)
End Function
' JapaneseEraName2の値を元号の略称へ変換するためのテーブル
Private EraShortNames2 As New Dictionary(Of JapaneseEraName2, String) _
From
{
{JapaneseEraName2.Meiji, "M"},
{JapaneseEraName2.Taisho, "T"},
{JapaneseEraName2.Showa, "S"},
{JapaneseEraName2.Heisei, "H"}
}
' JapaneseEraName2の値を元号の略称へ変換する拡張メソッド
<System.Runtime.CompilerServices.Extension()>
Public Function ToShortName(era As JapaneseEraName2) As String
Return EraShortNames2(era)
End Function
End Module
……省略……
Dim era = JapaneseEraName2.Heisei
Dim eraFullName As String = era.ToFullName()
Dim eraShortName As String = era.ToShortName()
WriteLine($"{eraFullName}({eraShortName})")
' 出力:平成(H)
列挙子に割り当てた整数が0始まりで連続しているときは、変換テーブルに代えて次のコードのように文字列の配列が使える(多少の不連続があっても可能)。
public enum JapaneseEraName3 { Meiji, Taisho, Showa, Heisei, }
……省略……
// JapaneseEraName3の値をインデックスとする元号の正式名称の配列
static string[] EraFullNames3 = { "明治", "大正", "昭和", "平成", };
// JapaneseEraName3の値をインデックスとする元号の略称の配列
static string[] EraShortNames3 = { "M", "T", "S", "H", };
……省略……
var era = JapaneseEraName3.Heisei;
string eraFullName = EraFullNames3[(int)era];
string eraShortName = EraShortNames3[(int)era];
WriteLine($"{eraFullName}({eraShortName})");
// 出力:平成(H)
Public Enum JapaneseEraName3
Meiji
Taisho
Showa
Heisei
End Enum
……省略……
' JapaneseEraName3の値をインデックスとする元号の正式名称の配列
Private EraFullNames3 As String() = {"明治", "大正", "昭和", "平成"}
' JapaneseEraName3の値をインデックスとする元号の略称の配列
Private EraShortNames3 As String() = {"M", "T", "S", "H"}
……省略……
Dim era = JapaneseEraName3.Heisei
Dim eraFullName As String = EraFullNames3(era)
Dim eraShortName As String = EraShortNames3(era)
WriteLine($"{eraFullName}({eraShortName})")
' 出力:平成(H)
列挙値を任意の文字列に変換するには、変換テーブルか配列を参照する。その変換ロジックは拡張メソッドにしておくとコードが分かりやすくなる。特に配列を使うときには、将来の仕様変更に備えて、変換ロジックを拡張メソッドにカプセル化しておくとよい。
利用可能バージョン:.NET Framework 1.0以降(サンプルコードにはそれ以降の機能/構文も含む)
カテゴリ:クラス・ライブラリ 処理対象:列挙体
使用ライブラリ:Enumクラス(System名前空間)
関連TIPS:列挙体の値を列挙するには?
関連TIPS:列挙体の名前を列挙するには?
関連TIPS:列挙体をビット・フィールドとして取り扱うには?[C#、VB]
関連TIPS:Dictionaryクラスを簡単に初期化するには?[C# 3.0]
関連TIPS:構文:メソッドやプロパティをラムダ式で簡潔に実装するには?[C# 6.0]
関連TIPS:構文:クラス名を書かずに静的メソッドを呼び出すには?[C# 6.0]
関連TIPS:VB.NETでクラス名を省略してメソッドや定数を利用するには?
関連TIPS:数値を右詰めや0埋めで文字列化するには?[C#、VB]
関連TIPS:Visual Studioでコンソール・アプリケーションのデバッグ実行時にコマンド・プロンプトを閉じないようにするには?
Copyright© Digital Advantage Corp. All Rights Reserved.