que enum define como acceder c# generics casting enums

define - Cast Int para Enum genérico en C#



enum in model c# (5)

Alternativamente, si puede obtener una enumeración no como un tipo genérico, sino como un tipo, simplemente use

Enum.ToObject

https://msdn.microsoft.com/en-us/library/system.enum.toobject(v=vs.110).aspx

Similar a Cast int to enum en C # pero my enum es un parámetro de tipo genérico. ¿Cuál es la mejor manera de manejar esto?

Ejemplo:

private T ConvertEnum<T>(int i) where T : struct, IConvertible { return (T)i; }

Genera el error del compilador Cannot convert type ''int'' to ''T''

El código completo es el siguiente, donde value puede contener el int o null.

private int? TryParseInt(string value) { var i = 0; if (!int.TryParse(value, out i)) { return null; } return i; } private T? TryParseEnum<T>(string value) where T : struct, IConvertible { var i = TryParseInt(value); if (!i.HasValue) { return null; } return (T)i.Value; }


Aquí hay una solución muy rápida que abusa del hecho de que el tiempo de ejecución crea múltiples instancias de clases genéricas estáticas. ¡Desata tus demonios de optimización interna!

Esto realmente brilla cuando estás leyendo Enums de una transmisión de una manera genérica. Combínelo con una clase externa que también almacena en caché el tipo subyacente de la enumeración y un BitConverter para liberar lo increíble.

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); }

Resultados en Core i7-3740QM con optimizaciones habilitadas:

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



La forma más simple que he encontrado es forzar la mano del compilador agregando un molde a un object .

return (T)(object)i.Value;


public static class Extensions { public static T ToEnum<T>(this int param) { var info = typeof(T); if (info.IsEnum) { T result = (T)Enum.Parse(typeof(T), param.ToString(), true); return result; } return default(T); } }