【问题标题】:Get max value from enum using generics使用泛型从枚举中获取最大值
【发布时间】:2019-06-05 06:58:09
【问题描述】:

如何使用泛型从枚举中获取最大 int 值?

我尝试了以下方法,但它显示以下编译错误:

无法将 T 隐式转换为 int

    int maxValue = GetMaxValue<SomeEnum>(typeof(SomeEnum)); //expecting 2

    private static int GetMaxValue<T>(Type enumType)
    {
        return Enum.GetValues(enumType).Cast<T>().Max();
    }

    public enum SomeEnum
    {
        ValueOne = 1,
        Value = 2
    }

【问题讨论】:

  • 枚举只能定义为int,为什么要使用泛型并尝试强制转换?
  • @ALFA 其实枚举也可以定义为字节、短或长

标签: c# enums


【解决方案1】:

在 C# 7.3 或更高版本的情况下,您可以以稍微不同的方式实现 Sweeper 的 想法(借助 where T : Enum 约束):

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

...

SomeEnum max = GetMaxValue<SomeEnum>();

请注意,结果是enum 本身,这就是为什么我们对枚举基础类型没有任何问题(byteshortintlong

【讨论】:

    【解决方案2】:

    您需要转换为int,而不是T。而且你实际上并不需要Type 参数(除非你在编译时不知道类型),因为你可以只做typeof(T)

    private static int GetMaxValue<T>()
    {
        return Enum.GetValues(typeof(T)).Cast<int>().Max();
    }
    
    // usage:
    GetMaxValue<SomeEnum>() // 2
    

    如果您的枚举有 long 或其他类型作为基础类型,您可以指定另一个类型参数将它们强制转换为:

    private static U GetMaxValue<T, U>() where U : struct
    {
        return Enum.GetValues(typeof(T)).Cast<U>().Max();
    }
    
    // usage:
    GetMaxValue<SomeLongEnum, long>()
    

    【讨论】:

    • 如果你的枚举被定义为long(或byteshort),这将不起作用。最好使用Convert.ToInt32 来覆盖这些情况(尽管它显然没有用long 覆盖溢出情况,但是没有办法用那个签名来覆盖它)
    • 我认为你可以通过强制转换来获得long 枚举(int 是默认值),所以当你转换回int 时应该不会产生任何问题,对吧?
    • @ALFA 如果值大于int.MaxValue会这样
    • @KevinGosse 我的想法是你不能有一个大于int.MaxValue 的值,如果为了有一个long 枚举首先你必须从int 转换为long 类型。
    • 枚举是一组命名常量,其基础类型是任何整数类型Enum Class
    【解决方案3】:

    使用Convert.ToInt32

     return Convert.ToInt32(Enum.GetValues(enumType).Cast<T>().Max());
    

    但通常我这样做,比调用 GetValues 更快

    public enum SomeEnum
    {
        ValueOne = 1,
        Value = 2,
        END
    }
    
    return (int)(SomeEnum.END - 1);
    

    【讨论】:

      猜你喜欢
      • 1970-01-01
      • 1970-01-01
      • 1970-01-01
      • 2010-09-17
      • 1970-01-01
      • 1970-01-01
      • 1970-01-01
      • 1970-01-01
      • 1970-01-01
      相关资源
      最近更新 更多