170

列挙型の最大値を取得するにはどうすればよいですか?

4

11 に答える 11

244

Enum.GetValues() は値を順番に返すように見えるので、次のようなことができます:

// given this enum:
public enum Foo
{
    Fizz = 3, 
    Bar = 1,
    Bang = 2
}

// this gets Fizz
var lastFoo = Enum.GetValues(typeof(Foo)).Cast<Foo>().Last();

編集

コメントを読みたくない方へ: 次の方法でも可能です:

var lastFoo = Enum.GetValues(typeof(Foo)).Cast<Foo>().Max();

...列挙値の一部が負の場合に機能します。

于 2008-10-15T01:05:10.003 に答える
52

マットの答えに同意します。最小値と最大値の int 値だけが必要な場合は、次のように実行できます。

最大:

Enum.GetValues(typeof(Foo)).Cast<int>().Max();

最小:

Enum.GetValues(typeof(Foo)).Cast<int>().Min();
于 2013-07-12T15:30:25.263 に答える
22

Matt Hamilton の回答によると、そのための Extension メソッドを作成することを考えました。

ValueTypeはジェネリック型パラメーターの制約として受け入れられないため、次のように制限するより良い方法は見つかりませんでしTEnum

どんなアイデアでも大歓迎です。

PS。私の VB の暗黙性は無視してください。私はこのように VB を使用するのが大好きです。それが VB の強みであり、VB が大好きな理由です。

ただし、ここにあります:

C#:

static void Main(string[] args)
{
    MyEnum x = GetMaxValue<MyEnum>(); //In newer versions of C# (7.3+)
    MyEnum y = GetMaxValueOld<MyEnum>();  
}

public static TEnum GetMaxValue<TEnum>()
  where TEnum : Enum
{
     return Enum.GetValues(typeof(TEnum)).Cast<TEnum>().Max();
}

//When C# version is smaller than 7.3, use this:
public static TEnum GetMaxValueOld<TEnum>()
  where TEnum : IComparable, IConvertible, IFormattable
{
    Type type = typeof(TEnum);

    if (!type.IsSubclassOf(typeof(Enum)))
        throw new
            InvalidCastException
                ("Cannot cast '" + type.FullName + "' to System.Enum.");

    return (TEnum)Enum.ToObject(type, Enum.GetValues(type).Cast<int>().Last());
}



enum MyEnum
{
    ValueOne,
    ValueTwo
}

VB:

Public Function GetMaxValue _
    (Of TEnum As {IComparable, IConvertible, IFormattable})() As TEnum

    Dim type = GetType(TEnum)

    If Not type.IsSubclassOf(GetType([Enum])) Then _
        Throw New InvalidCastException _
            ("Cannot cast '" & type.FullName & "' to System.Enum.")

    Return [Enum].ToObject(type, [Enum].GetValues(type) _
                        .Cast(Of Integer).Last)
End Function
于 2009-08-20T00:52:28.590 に答える
13

これは少し厄介ですが、 any の実際の最大値enumは(から派生したものInt32.MaxValueであると仮定して) です。実際にその値を持つメンバーを宣言したかどうかに関係なく 、任意の値をany にキャストすることは完全に合法です。enumintInt32enum

法的:

enum SomeEnum
{
    Fizz = 42
}

public static void SomeFunc()
{
    SomeEnum e = (SomeEnum)5;
}
于 2008-10-15T08:13:31.793 に答える
10

もう一度試した後、次の拡張メソッドを取得しました。

public static class EnumExtension
{
    public static int Max(this Enum enumType)
    {           
        return Enum.GetValues(enumType.GetType()).Cast<int>().Max();             
    }
}

class Program
{
    enum enum1 { one, two, second, third };
    enum enum2 { s1 = 10, s2 = 8, s3, s4 };
    enum enum3 { f1 = -1, f2 = 3, f3 = -3, f4 };

    static void Main(string[] args)
    {
        Console.WriteLine(enum1.one.Max());        
    }
}
于 2009-11-03T08:19:49.130 に答える
5

Last 関数を使用して最大値を取得できませんでした。「最大」機能を使用できます。お気に入り:

 class Program
    {
        enum enum1 { one, two, second, third };
        enum enum2 { s1 = 10, s2 = 8, s3, s4 };
        enum enum3 { f1 = -1, f2 = 3, f3 = -3, f4 };

        static void Main(string[] args)
        {
            TestMaxEnumValue(typeof(enum1));
            TestMaxEnumValue(typeof(enum2));
            TestMaxEnumValue(typeof(enum3));
        }

        static void TestMaxEnumValue(Type enumType)
        {
            Enum.GetValues(enumType).Cast<Int32>().ToList().ForEach(item =>
                Console.WriteLine(item.ToString()));

            int maxValue = Enum.GetValues(enumType).Cast<int>().Max();     
            Console.WriteLine("The max value of {0} is {1}", enumType.Name, maxValue);
        }
    }
于 2009-11-03T07:34:58.783 に答える
4

Matthew J Sullivanとの合意により、C#の場合:

   Enum.GetValues(typeof(MyEnum)).GetUpperBound(0);

なぜ誰かが使いたいのかよくわかりません:

   Enum.GetValues(typeof(MyEnum)).Cast<MyEnum>().Last();

...一言一句、意味的に言えば、それはそれほど意味がないように思われますか?(さまざまな方法があることは常に良いことですが、後者の利点はわかりません。)

于 2010-02-23T18:34:57.563 に答える
2

System.Enumの下に列挙型に関する情報を取得するためのメソッドがあります。

したがって、Visual StudioのVB.Netプロジェクトでは、「System.Enum」と入力できます。インテリセンスはあらゆる種類の善をもたらします。

特に1つのメソッドはSystem.Enum.GetValues()で、列挙値の配列を返します。アレイを取得したら、特定の状況に適した処理を実行できるようになります。

私の場合、列挙値はゼロから始まり、数値をスキップしなかったため、列挙型の最大値を取得するには、配列に含まれる要素の数を知る必要があります。

VB.Netコードスニペット:

'''''''

Enum MattType
  zerothValue         = 0
  firstValue          = 1
  secondValue         = 2
  thirdValue          = 3
End Enum

'''''''

Dim iMax      As Integer

iMax = System.Enum.GetValues(GetType(MattType)).GetUpperBound(0)

MessageBox.Show(iMax.ToString, "Max MattType Enum Value")

'''''''
于 2009-09-03T22:57:55.610 に答える
1

F# では、列挙型をシーケンスに変換するヘルパー関数を使用します。

type Foo =
    | Fizz  = 3
    | Bang  = 2

// Helper function to convert enum to a sequence. This is also useful for iterating.
// stackoverflow.com/questions/972307/can-you-loop-through-all-enum-values-c
let ToSeq (a : 'A when 'A : enum<'B>) =
    Enum.GetValues(typeof<'A>).Cast<'B>()

// Get the max of Foo
let FooMax = ToSeq (Foo()) |> Seq.max   

それを実行しています...

> タイプ Foo = | フィズ = 3 | 強打 = 2
> val ToSeq : 'A -> seq<'B> when 'A : enum<'B>
> val FooMax : Foo = フィズ

when 'A : enum<'B>、コンパイラによる定義には必要ありませんが、有効な列挙型であっても、ToSeq を使用するために必要です。

于 2011-08-20T07:31:16.660 に答える