Вот очень быстрое решение, которое злоупотребляет фактом что среда выполнения создает несколько экземпляров статических родовых классов. Развяжите свои внутренние демоны оптимизации!
Это действительно сияет, когда вы читаете Enums из потока в общем виде. Комбинируйте с внешним классом, который также кэширует базовый тип перечисления и битконвертер, чтобы развязать удивительный.
void Main()
{
Console.WriteLine("Cast (reference): {0}", (TestEnum)5);
Console.WriteLine("EnumConverter: {0}", EnumConverter<TestEnum>.Convert(5));
Console.WriteLine("Enum.ToObject: {0}", Enum.ToObject(typeof(TestEnum), 5));
int iterations = 1000 * 1000 * 100;
Measure(iterations, "Cast (reference)",() => { var t = (TestEnum)5; });
Measure(iterations, "EnumConverter",() => EnumConverter<TestEnum>.Convert(5));
Measure(iterations, "Enum.ToObject",() => Enum.ToObject(typeof(TestEnum), 5));
}
static class EnumConverter<TEnum> where TEnum : struct, IConvertible
{
public static readonly Func<long, TEnum> Convert = GenerateConverter();
static Func<long, TEnum> GenerateConverter()
{
var parameter = Expression.Parameter(typeof(long));
var dynamicMethod = Expression.Lambda<Func<long, TEnum>>(
Expression.Convert(parameter, typeof(TEnum)),
parameter);
return dynamicMethod.Compile();
}
}
enum TestEnum
{
Value = 5
}
static void Measure(int repetitions, string what, Action action)
{
action();
var total = Stopwatch.StartNew();
for (int i = 0; i < repetitions; i++)
{
action();
}
Console.WriteLine("{0}: {1}", what, total.Elapsed);
}
Результатов на ядро i7-3740QM с поддержкой оптимизацией:
Cast (reference): Value
EnumConverter: Value
Enum.ToObject: Value
Cast (reference): 00:00:00.3175615
EnumConverter: 00:00:00.4335949
Enum.ToObject: 00:00:14.3396366
http://stackoverflow.com/questions/2745320/enum-tryparse-with-flags-attribute - может помочь ? – Sunny
Последний ответ на http://stackoverflow.com/questions/1331739/enum-type-constraints-in-c-sharp ближе к тому, что вы хотите. Тем не менее, это все еще не умно. Я склонен использовать рефлексию для этого, вы можете сделать код намного сильнее. Struct не является достаточно доступным для того, чтобы пообщаться с дженериками, на мой взгляд. –
Что-то не в коробке: [c-sharp-non-boxing-conversion-of-generic-enum-to-int] (http://stackoverflow.com/questions/1189144/c-sharp-non-boxing- conversion-of-generic-enum-to-int) – nawfal