C#枚举
-
值类型
-
设置底层类型和显式值
-
enum Enum : ulong { // 类似继承的方式设置底层类型,默认为int Green, // 0 Yellow = 10, // 10 Red, // 11 }
-
每个枚举类型都有一个底层值,默认为int,第一个成员默认为0,后面比前面多1
-
如果给其中某个成员赋值,则再后面没有显式赋值的成员会继续在前面的基础上+1
-
如果显式值过大超出了int的范围,可以设置底层类型为long或者ulong,底层类型可以是任何整数类型
-
关联到成员名称的值不需要是独特的,如可以允许多个成员使用同样的值
-
也可以使用该枚举类型中的成员给其他成员赋值
-
-
位标志
-
标志变量的压缩,把多个标志变量压缩到同一个变量里表示,类似C++中的 bitset?
-
可以通过或运算
|
来标志多个位 -
可以通过HasFlag判断该位是否被标记,如果是多个位可以对要判断的位相或
-
也可以通过&来判断标记
-
[Flags] // Flags特性 enum FlagsEnum { first = 0x01, second = 0x02, third = 0x04, forth = 0x08 } FlagsEnum flags = FlagsEnum.second | FlagsEnum.third; bool f1 = flags.HasFlag(FlagsEnum.second); bool f2 = flags.HasFlag(FlagsEnum.first | FlagsEnum.third); // 注意逻辑,虽然后面是两个条件的相或,但是HasFlag本身是和与逻辑对应的,所以是两个标志位都检查的 bool f3 = ((flags & FlagsEnum.forth) == FlagsEnum.forth);
-
Flags特性
- 虽然不改变计算结果,但是提供了一些方便的特性
- 首先是通知编译器、对象浏览器等,该枚举可以按位标志进行组合
- 其次是格式化输出
- 我们知道对于枚举类型,直接输出和ToString()均为返回字符串
- 但是对于上面代码中的flags这种经过或运算的值,如果不加Flags特性时输出为计算后的整数,因为在调用ToString时没有找到值为12对应的枚举成员的字符串,所以会输出整数12
- 加上Flags特性后,会将12对应两个分开的位标志成员,输出为两个字符串并用逗号和空格隔开
-
-
补充
-
枚举只有单一的成员类型:声明的成员常量
-
不同枚举类型之间不能比较大小
-
枚举类型可以枚举
-
enum MyEnum { first, second, third } for (MyEnum e = MyEnum.first; e <= MyEnum.third; e++) { System.Console.WriteLine(e); }
-
但是注意上面这段代码,如果在枚举声明时有赋值操作,则在遍历时会有中间没有声明的整数被枚举到
-
-
Enum类型还包含一些静态方法,如GetNames、GetName、IsDefine等,多数都有泛型与非泛型两种使用方式,但是泛型的版本,如果有第二个参数的话必须是枚举,非泛型版本可以使用整数或字符串
-
GetNames:参数为枚举的类型(Type),返回所有成员名称的字符串数组,泛型版本无参数
-
string[] myEnums = Enum.GetNames(typeof(MyEnum)); // 也可以使用Enum.GetNames<MyEnum>() foreach (var myEnum in myEnums) { System.Console.WriteLine(myEnum); }
-
GetName:参数为枚举的类型(Type)和整数,返回成员名称的字符串,如果不存在则返回null
-
IsDefined:参数为枚举的类型(Type)和整数或字符串,如果在枚举中定义了该项则返回true
-
-