如何使用Generics创建一种从枚举中创建IEnumerable的方法?

鉴于这样的枚举:

public enum City { London = 1, Liverpool = 20, Leeds = 25 } public enum House { OneFloor = 1, TwoFloors = 2 } 

我使用以下代码给我一个IEnumerable:

 City[] values = (City[])Enum.GetValues(typeof(City)); var valuesWithNames = from value in values select new { value = (int)value, name = value.ToString() }; 

代码工作得很好但是我必须为很多枚举做这个。 有没有办法可以创建这样做的通用方法?

此function可能会帮助您:

 public static IEnumerable> GetValues() where T : struct { var t = typeof(T); if(!t.IsEnum) throw new ArgumentException("Not an enum type"); return Enum.GetValues(t).Cast().Select (x => new KeyValuePair( (int)Enum.ToObject(t, x), x.ToString())); } 

用法:

 var values = GetValues(); 

使用Jon Skeet 无拘无束的旋律 。

 using UnconstrainedMelody; 

您可以将枚举值放入Dictionary ,然后枚举它们:

 var valuesAsDictionary = Enums.GetValues() .ToDictionary(key => (int)key, value => value.ToString()); 

但你可能甚至不需要这样做。 为什么不直接枚举值:

 foreach (var value in Enums.GetValues()) { Console.WriteLine("{0}: {1}", (int)value, value); } 

为什么不:

  IEnumerable GetValues() { return Enum.GetValues(typeof (T)) .Cast() .Select(value => new { value = Convert.ToInt32(value), name = value.ToString() }); } 

所以你可以使用:

 var result = GetValues(); 

如果你想将约束genericsT作为enum ,因为enum 不能直接用作通用约束,但枚举inheritance自IConvertible接口,相信这种方式是可以的:

 IEnumerable GetValues() where T: struct, IConvertible {} 

要通过Dictionary替换IEnumerable

 Dictionary GetValues() where T : struct, IConvertible { return Enum.GetValues(typeof (T)).Cast() .ToDictionary(value => Convert.ToInt32(value), value => value.ToString()); } 

编辑 :作为马格努斯的评论,如果你需要确定项目的顺序,字典不是选项。 定义自己的强类型会更好。