サーチ…
前書き
列挙型は、byte、sbyte、short、ushort、int、uint、long、ulongのいずれかの型から派生することができます。デフォルトはintで、enum定義で型を指定することで変更できます:
Weekday:byte {Monday = 1、Tuesday = 2、Wednesday = 3、Thursday = 4、Friday = 5}
これは、P /ネイティブコードへの呼び出し、データソースへのマッピング、および同様の状況で有用です。一般に、デフォルトのintを使うべきです、なぜなら、ほとんどの開発者はenumがintであると予想しているからです。
構文
- 列挙型の色{赤、緑、青} // Enum宣言
- enum色:byte {赤、緑、青} //特定の型の宣言
- 列挙型の色{赤= 23、緑= 45、青= 12} //定義された値を持つ宣言
- Colors.Red // Enumの要素にアクセスする
- int value =(int)Colors.Red // enum要素のint値を取得する
- Colors color =(Colors)intValue // intからenum要素を取得する
備考
Enum(列挙型の略)は、型固有の識別子で表される名前付き定数のセットからなる型です。
列挙型は、(通常は小さな)可能な離散値を持つ概念を表現するのに最も有用です。たとえば、曜日や月を表すのに使用できます。これらは、ビット単位の操作を使用して結合またはチェックできるフラグとしても使用できます。
列挙型のすべてのメンバー値を取得する
enum MyEnum
{
One,
Two,
Three
}
foreach(MyEnum e in Enum.GetValues(typeof(MyEnum)))
Console.WriteLine(e);
これは印刷されます:
One
Two
Three
フラグとしての列挙型
FlagsAttribute
を列挙型に適用して、列挙型の性質に合わせてToString()
動作を変更することができます。
[Flags]
enum MyEnum
{
//None = 0, can be used but not combined in bitwise operations
FlagA = 1,
FlagB = 2,
FlagC = 4,
FlagD = 8
//you must use powers of two or combinations of powers of two
//for bitwise operations to work
}
var twoFlags = MyEnum.FlagA | MyEnum.FlagB;
// This will enumerate all the flags in the variable: "FlagA, FlagB".
Console.WriteLine(twoFlags);
FlagsAttribute
は列挙定数が2の累乗(またはその組み合わせ)に依存し、列挙値は最終的に数値であるため、基礎となる数値型のサイズによって制限されます。使用できる最大の数値型はUInt64
、64個の別個の(結合されていない)フラグ列挙定数を指定できます。 enum
キーワードのデフォルトは、基になる型int
( Int32
です。コンパイラは、32ビットより広い値の宣言を許可します。それらは警告なしにラップアラウンドし、同じ値の2つ以上の列挙型メンバーになります。したがって、enumが32以上のフラグのビットセットに対応する場合は、より大きな型を明示的に指定する必要があります。
public enum BigEnum : ulong
{
BigValue = 1 << 63
}
フラグはしばしば単一のビットですが、より使いやすくするために名前付きの "セット"に結合することができます。
[Flags]
enum FlagsEnum
{
None = 0,
Option1 = 1,
Option2 = 2,
Option3 = 4,
Default = Option1 | Option3,
All = Option1 | Option2 | Option3,
}
2の累乗の10進値のスペルを避けるために、 左シフト演算子(<<)を使用して同じ列挙型を宣言することもできます
[Flags]
enum FlagsEnum
{
None = 0,
Option1 = 1 << 0,
Option2 = 1 << 1,
Option3 = 1 << 2,
Default = Option1 | Option3,
All = Option1 | Option2 | Option3,
}
C#7.0以降、 バイナリリテラルも使用できます。
enum変数の値に特定のフラグが設定されているかどうかを確認するには、 HasFlag
メソッドを使用できます。私たちが持っているとしましょう
[Flags]
enum MyEnum
{
One = 1,
Two = 2,
Three = 4
}
そしてvalue
var value = MyEnum.One | MyEnum.Two;
HasFlag
を使用すると、フラグが設定されているかどうかを確認できます
if(value.HasFlag(MyEnum.One))
Console.WriteLine("Enum has One");
if(value.HasFlag(MyEnum.Two))
Console.WriteLine("Enum has Two");
if(value.HasFlag(MyEnum.Three))
Console.WriteLine("Enum has Three");
また、enumのすべての値を繰り返して、設定されているすべてのフラグを取得することもできます
var type = typeof(MyEnum);
var names = Enum.GetNames(type);
foreach (var name in names)
{
var item = (MyEnum)Enum.Parse(type, name);
if (value.HasFlag(item))
Console.WriteLine("Enum has " + name);
}
または
foreach(MyEnum flagToCheck in Enum.GetValues(typeof(MyEnum)))
{
if(value.HasFlag(flagToCheck))
{
Console.WriteLine("Enum has " + flagToCheck);
}
}
3つの例すべてが印刷されます:
Enum has One
Enum has Two
ビット単位の論理を持つフラグ形式のenum値をテストする
flags-style列挙型の値は、単一の値と一致しない可能性があるため、ビット単位の論理でテストする必要があります。
[Flags]
enum FlagsEnum
{
Option1 = 1,
Option2 = 2,
Option3 = 4,
Option2And3 = Option2 | Option3;
Default = Option1 | Option3,
}
Default
値は、実際には、ビット単位のORでマージされた2つの組み合わせです。したがって、フラグの存在をテストするには、ビット単位のANDを使用する必要があります。
var value = FlagsEnum.Default;
bool isOption2And3Set = (value & FlagsEnum.Option2And3) == FlagsEnum.Option2And3;
Assert.True(isOption2And3Set);
文字列と列挙の列挙
public enum DayOfWeek
{
Sunday,
Monday,
Tuesday,
Wednesday,
Thursday,
Friday,
Saturday
}
// Enum to string
string thursday = DayOfWeek.Thursday.ToString(); // "Thursday"
string seventhDay = Enum.GetName(typeof(DayOfWeek), 6); // "Saturday"
string monday = Enum.GetName(typeof(DayOfWeek), DayOfWeek.Monday); // "Monday"
// String to enum (.NET 4.0+ only - see below for alternative syntax for earlier .NET versions)
DayOfWeek tuesday;
Enum.TryParse("Tuesday", out tuesday); // DayOfWeek.Tuesday
DayOfWeek sunday;
bool matchFound1 = Enum.TryParse("SUNDAY", out sunday); // Returns false (case-sensitive match)
DayOfWeek wednesday;
bool matchFound2 = Enum.TryParse("WEDNESDAY", true, out wednesday); // Returns true; DayOfWeek.Wednesday (case-insensitive match)
// String to enum (all .NET versions)
DayOfWeek friday = (DayOfWeek)Enum.Parse(typeof(DayOfWeek), "Friday"); // DayOfWeek.Friday
DayOfWeek caturday = (DayOfWeek)Enum.Parse(typeof(DayOfWeek), "Caturady"); // Thows ArgumentException
// All names of an enum type as strings
string[] weekdays = Enum.GetNames(typeof(DayOfWeek));
enumのデフォルト値== ZERO
列挙型のデフォルト値はゼロです。列挙型で値が0の項目が定義されていない場合、そのデフォルト値はゼロになります。
public class Program
{
enum EnumExample
{
one = 1,
two = 2
}
public void Main()
{
var e = default(EnumExample);
if (e == EnumExample.one)
Console.WriteLine("defaults to one");
else
Console.WriteLine("Unknown");
}
}
例: https : //dotnetfiddle.net/l5Rwie
列挙型の基礎
MSDNから:
列挙型(列挙型または列挙型)は、変数に割り当てることができる名前付き整数定数のセットを効率的に定義する方法を提供します 。
本質的に、列挙型は有限オプションのセットのみを許可するタイプであり、各オプションは数値に対応します。デフォルトでは、値がゼロから始まる順に増加しています。たとえば、曜日の列挙型を宣言することができます。
public enum Day
{
Monday,
Tuesday,
Wednesday,
Thursday,
Friday,
Saturday,
Sunday
}
その列挙型は次のように使用できます:
// Define variables with values corresponding to specific days
Day myFavoriteDay = Day.Friday;
Day myLeastFavoriteDay = Day.Monday;
// Get the int that corresponds to myFavoriteDay
// Friday is number 4
int myFavoriteDayIndex = (int)myFavoriteDay;
// Get the day that represents number 5
Day dayFive = (Day)5;
デフォルトではenum
各要素の基本型はint
ですが、 byte
、 sbyte
、 short
、 ushort
、 uint
、 long
、およびulong
も同様に使用できます。 int
以外の型を使用する場合は、列挙型の名前の後にコロンを使用して型を指定する必要があります。
public enum Day : byte
{
// same as before
}
名前の後の数字は、整数ではなくバイトです。列挙型の基礎となる型を次のように取得できます。
Enum.GetUnderlyingType(typeof(Days)));
出力:
System.Byte
デモ: .NET fiddle
列挙型を用いたビット操作
FlagsAttributeは、列挙型が単一の値ではなくフラグのコレクションを表すときは常に使用する必要があります。各enum値に割り当てられた数値は、ビット演算子を使用してenumを操作するときに役立ちます。
例1:[フラグ]
[Flags]
enum Colors
{
Red=1,
Blue=2,
Green=4,
Yellow=8
}
var color = Colors.Red | Colors.Blue;
Console.WriteLine(color.ToString());
赤、青を印刷します。
例2:[フラグ]がない場合
enum Colors
{
Red=1,
Blue=2,
Green=4,
Yellow=8
}
var color = Colors.Red | Colors.Blue;
Console.WriteLine(color.ToString());
プリント3
フラグに<<表記を使用する
左シフト演算子( <<
)はフラグenum宣言で使用することができ、各フラグのフラグは必ずバイナリ表現で1
になります。
これはまた、大量の列挙型のフラグがたくさんある大きな列挙体の可読性を向上させるのに役立ちます。
[Flags]
public enum MyEnum
{
None = 0,
Flag1 = 1 << 0,
Flag2 = 1 << 1,
Flag3 = 1 << 2,
Flag4 = 1 << 3,
Flag5 = 1 << 4,
...
Flag31 = 1 << 30
}
MyEnum
は適切なフラグだけが含まれており、不適切なFlag30 = 1073741822
(または111111111111111111111111111110バイナリ)のような乱雑なものは含まれていないことは明らかです。
enum値に追加の説明情報を追加する
場合によっては、enum値自体にユーザーに表示したいものより読みにくい場合など、追加の説明をenum値に追加することができます。そのような場合は、 System.ComponentModel.DescriptionAttribute
クラスを使用できます。
例えば:
public enum PossibleResults
{
[Description("Success")]
OK = 1,
[Description("File not found")]
FileNotFound = 2,
[Description("Access denied")]
AccessDenied = 3
}
特定のenum値の説明を返す場合は、次のようにします。
public static string GetDescriptionAttribute(PossibleResults result)
{
return ((DescriptionAttribute)Attribute.GetCustomAttribute((result.GetType().GetField(result.ToString())), typeof(DescriptionAttribute))).Description;
}
static void Main(string[] args)
{
PossibleResults result = PossibleResults.FileNotFound;
Console.WriteLine(result); // Prints "FileNotFound"
Console.WriteLine(GetDescriptionAttribute(result)); // Prints "File not found"
}
これは、すべての列挙型の拡張メソッドに簡単に変換することもできます。
static class EnumExtensions
{
public static string GetDescription(this Enum enumValue)
{
return ((DescriptionAttribute)Attribute.GetCustomAttribute((enumValue.GetType().GetField(enumValue.ToString())), typeof(DescriptionAttribute))).Description;
}
}
そして、次のように簡単に使用します: Console.WriteLine(result.GetDescription());
フラグ付き列挙型の値を追加および削除する
このコードは、フラグを付けたenum-instanceから値を追加したり削除したりするためのものです。
[Flags]
public enum MyEnum
{
Flag1 = 1 << 0,
Flag2 = 1 << 1,
Flag3 = 1 << 2
}
var value = MyEnum.Flag1;
// set additional value
value |= MyEnum.Flag2; //value is now Flag1, Flag2
value |= MyEnum.Flag3; //value is now Flag1, Flag2, Flag3
// remove flag
value &= ~MyEnum.Flag2; //value is now Flag1, Flag3
列挙型は予期しない値を持つ可能性があります
列挙型は基本的な整数型との間でキャストすることができるため、値は列挙型の定義で指定された値の範囲外になることがあります。
以下の列挙型のDaysOfWeek
は7つの定義済みの値しかありDaysOfWeek
んが、それでもint
値を保持できます。
public enum DaysOfWeek
{
Monday = 1,
Tuesday = 2,
Wednesday = 3,
Thursday = 4,
Friday = 5,
Saturday = 6,
Sunday = 7
}
DaysOfWeek d = (DaysOfWeek)31;
Console.WriteLine(d); // prints 31
DaysOFWeek s = DaysOfWeek.Sunday;
s++; // No error
現在のところ、この動作を持たない列挙型を定義する方法はありません。
ただし、 Enum.IsDefined
メソッドを使用すると、未定義のenum値を検出できます。例えば、
DaysOfWeek d = (DaysOfWeek)31;
Console.WriteLine(Enum.IsDefined(typeof(DaysOfWeek),d)); // prints False