1. 程式人生 > >C#6.0語言規範(十四) 枚舉

C#6.0語言規範(十四) 枚舉

invalid 類的繼承 關鍵字 其他 abs ati ring 比較 code

一個枚舉類型是一個獨特的值類型(值類型)聲明一組命名的常量。

這個例子

1 enum Color
2 {
3     Red,
4     Green,
5     Blue
6 }

聲明了一個名為枚舉類型Color與成員RedGreenBlue

枚舉聲明

枚舉聲明聲明了一個新的枚舉類型。枚舉聲明以關鍵字開頭enum,並定義枚舉的名稱,可訪問性,基礎類型和成員。

 1 enum_declaration
 2     : attributes? enum_modifier* enum identifier enum_base? enum_body 
;? 3 ; 4 5 enum_base 6 : : integral_type 7 ; 8 9 enum_body 10 : { enum_member_declarations? } 11 | { enum_member_declarations , } 12 ;

每個枚舉類型都有一個相應的整數類型,稱為枚舉類型基礎類型。此基礎類型必須能夠表示枚舉中定義的所有枚舉器值。enum聲明可以顯式地聲明基礎類型的bytesbyteshortushortintuintlong

ulong請註意,char不能用作基礎類型。未明確聲明基礎類型的枚舉聲明具有基礎類型int

這個例子

1 enum Color: long
2 {
3     Red,
4     Green,
5     Blue
6 }

聲明一個基礎類型為的枚舉long開發人員可能會選擇使用基礎類型(long如示例中所示)來啟用範圍內long但不在範圍內的值int,或者為將來保留此選項。

枚舉修飾符

一個enum_declaration可任選地包括枚舉改性劑的一個序列:

1 enum_modifier
2     : new
3     | public
4 | protected 5 | internal 6 | private 7 ;

同一修飾符在枚舉聲明中多次出現是編譯時錯誤。

枚舉聲明的修飾符與類聲明(類修飾符)的含義相同但請註意,枚舉聲明中不允許使用abstractsealed修飾符。枚舉不能是抽象的,也不允許派生。

枚舉成員

枚舉類型聲明的主體定義零個或多個枚舉成員,它們是枚舉類型的命名常量。沒有兩個枚舉成員可以具有相同的名稱。

1 enum_member_declarations
2     : enum_member_declaration (, enum_member_declaration)*
3     ;
4 
5 enum_member_declaration
6     : attributes? identifier (= constant_expression)?
7     ;

每個枚舉成員都有一個關聯的常量值。此值的類型是包含枚舉的基礎類型。每個枚舉成員的常量值必須在枚舉的基礎類型的範圍內。這個例子

1 enum Color: uint
2 {
3     Red = -1,
4     Green = -2,
5     Blue = -3
6 }

導致編譯時錯誤,因為在恒定的值-1-2-3不在底層積分類型的範圍uint

多個枚舉成員可以共享相同的關聯值。這個例子

1 enum Color 
2 {
3     Red,
4     Green,
5     Blue,
6 
7     Max = Blue
8 }

顯示一個枚舉,其中兩個枚舉成員 - BlueMax- 具有相同的關聯值。

枚舉成員的關聯值是隱式或顯式指定的。如果枚舉成員的聲明具有constant_expression初始值設定項,則該常量表達式的值(隱式轉換為枚舉的基礎類型)是枚舉成員的關聯值。如果枚舉成員的聲明沒有初始值設定項,則隱式設置其關聯值,如下所示:

  • 如果枚舉成員是枚舉類型中聲明的第一個枚舉成員,則其關聯值為零。
  • 否則,通過將文本上在前的枚舉成員的關聯值增加1來獲得枚舉成員的關聯值。此增加的值必須在可由基礎類型表示的值範圍內,否則會發生編譯時錯誤。

這個例子

 1 using System;
 2 
 3 enum Color
 4 {
 5     Red,
 6     Green = 10,
 7     Blue
 8 }
 9 
10 class Test
11 {
12     static void Main() {
13         Console.WriteLine(StringFromColor(Color.Red));
14         Console.WriteLine(StringFromColor(Color.Green));
15         Console.WriteLine(StringFromColor(Color.Blue));
16     }
17 
18     static string StringFromColor(Color c) {
19         switch (c) {
20             case Color.Red: 
21                 return String.Format("Red = {0}", (int) c);
22 
23             case Color.Green:
24                 return String.Format("Green = {0}", (int) c);
25 
26             case Color.Blue:
27                 return String.Format("Blue = {0}", (int) c);
28 
29             default:
30                 return "Invalid color";
31         }
32     }
33 }

打印出枚舉成員名稱及其相關值。輸出是:

1 Red = 0
2 Green = 10
3 Blue = 11

原因如下:

  • 枚舉成員Red被自動賦值為零(因為它沒有初始值並且是第一個枚舉成員);
  • 枚舉成員Green被明確賦予值10;
  • 並且枚舉成員Blue被自動分配的值大於文本上位於其前面的成員。

枚舉成員的關聯值不能直接或間接使用其自己的關聯枚舉成員的值。除了這種循環限制之外,枚舉成員初始化器可以自由地引用其他枚舉成員初始化器,而不管它們的文本位置如何。在枚舉成員初始值設定項中,其他枚舉成員的值始終被視為具有其基礎類型的類型,因此在引用其他枚舉成員時不需要強制轉換。

這個例子

1 enum Circular
2 {
3     A = B,
4     B
5 }

導致編譯時錯誤,因為聲明AB是循環的。A取決於B明確,並B取決於A隱含。

枚舉成員的命名和範圍與類中的字段完全類似。枚舉成員的範圍是其包含枚舉類型的主體。在該範圍內,枚舉成員可以通過其簡單名稱來引用。在所有其他代碼中,枚舉成員的名稱必須使用其枚舉類型的名稱進行限定。枚舉成員沒有任何聲明的可訪問性 - 如果枚舉成員的包含枚舉類型可訪問,則可以訪問該成員。

System.Enum類型

類型System.Enum是所有枚舉類型的抽象基類(這與枚舉類型的基礎類型不同且不同),並且繼承自的成員System.Enum在任何枚舉類型中都可用。裝箱轉換(裝箱轉換)從任何枚舉類型來存在System.Enum,和取消裝箱轉換(解包轉換)從存在System.Enum於任何枚舉類型。

請註意,System.Enum它本身不是enum_type相反,它是一個class_type,從中派生所有enum_type該類型System.Enum繼承自類型System.ValueTypeSystem.ValueType類型),而類型繼承自類型object在運行時,type的值System.Enum可以是null或對任何枚舉類型的盒裝值的引用。

枚舉值和操作

每個枚舉類型定義一個不同的類型; 在枚舉類型和整數類型之間或兩個枚舉類型之間進行轉換需要式枚舉轉換(顯式枚舉轉換)。枚舉類型可以采用的值集不受其枚舉成員的限制。特別是,枚舉的基礎類型的任何值都可以強制轉換為枚舉類型,並且是該枚舉類型的唯一有效值。

枚舉成員具有包含枚舉類型的類型(在其他枚舉成員初始值設定項中除外:請參閱枚舉成員)。枚舉成員的值枚舉類型中聲明E相關聯的值v(E)v

以下運算符可以在枚舉類型的值可以使用:==!=<><=>=枚舉比較運算符),二進制+加法運算符),二進制-減法運算符), ,^& 枚舉邏輯運算符), 按位求補運算符),後綴增量和減量運算符以及前綴增量和減量運算符)。|~++--

每個枚舉類型都自動派生自類System.Enum(反過來,派生自System.ValueTypeobject)。因此,此類的繼承方法和屬性可用於枚舉類型的值。

C#6.0語言規範(十四) 枚舉