关于c#:迭代枚举类型

iterating on enum type

本问题已经有最佳答案,请猛点这里访问。

Possible Duplicate:
How do I enumerate an enum?

我不知道是否可以做我想做的事,但我想为什么不行。

我有示例枚举:

1
2
3
4
5
public enum Animals {
    Cat,
    Dog,
    ...
}

我要做的是迭代这个枚举。我希望它能像那样工作:

1
2
3
foreach( var type in Animals ) {
    Console.WriteLine( type.toString() );
}

输出为:

1
2
 Cat
 Dog

有可能吗?我不想把每个项都放到数组中,然后迭代,我想直接迭代这个枚举。


编辑:请注意,在这个答案中,我将Animals重命名为Animal。根据.NET约定,只有基于标志的枚举才应具有复数名称。

您可以使用Enum.GetValues()

1
2
3
foreach (var type in (Animal[]) Enum.GetValues(typeof(Animal)) {
    Console.WriteLine(type.toString());
}

如丹的评论中所述,如果在foreach循环中使用显式键入,则不需要强制转换:

1
2
3
foreach (Animal type in Enum.GetValues(typeof(Animal)) {
    Console.WriteLine(type.toString());
}

但现在你不会尽早发现错误。例如:

1
2
3
foreach (Animal type in Enum.GetValues(typeof(SomeEmptyEnum)) {
    Console.WriteLine(type.toString());
}

其中SomeEmptyEnum是(显然)空枚举类型。这里,GetValues将返回类型为SomeEmptyEnum[]的空数组。上面的代码将只检查返回数组的每个成员的类型是否正确,因此您不会发现问题。很明显,这在现实生活中不太可能发生,但它展示了一种代码味道,引导我转换结果——基本上,我更喜欢处理强类型集合。

或者,对于更安全的类型方法,您可以使用我的无约束旋律库:

1
2
3
foreach (var type in Enums.GetValues<Animal>()) {
    Console.WriteLine(type.ToString());
}

在这里,我的Enums.GetValues()返回IList,这意味着:

  • 不需要铸造
  • 它实际上返回一个不变的列表,因此不需要每次都创建一个新的集合,这与标准的Enum.GetValues()不同。

它还具有一个强制T为枚举类型的泛型约束,因此您不能意外地用非枚举类型调用它,不像Enum.GetValues()


试试这个:

1
2
3
4
5
6
7
8
9
10
11
12
13
14
    enum animals
    {
        cat,
        dog,
        fish
    }

    private void Form1_Load(object sender, EventArgs e)
    {
        foreach (string myAnimal in Enum.GetNames(typeof(animals)))
        {
            Debug.WriteLine(myAnimal);
        }
    }

您必须遍历enum.getNames(typeof(yourenum))。

祝你好运。


要在jon的答案中保存一些键入内容,请显式指定类型,您不必强制转换:

1
2
3
foreach (Animal a in Enum.GetValues(typeof(Animal)) {
    Console.WriteLine(a);
}

然而,正如乔恩所解释的那样,这也需要额外的谨慎。

还要注意,C枚举名称通常应为单数形式(Animal,而不是Animals),除非它们用允许组合的[Flags]属性标记。


使用enum.getNames()循环枚举成员的名称。使用enum.getValues()循环遍历这些值。


enum.getValues是您的朋友。