Hay muchas respuestas sobre cómo activar el tipo en versiones anteriores de C#. Mi pregunta tiene que ver con cómo activar el tipo llamado en un método genérico:
public T GetAxis<T>(object axisObject) { switch (typeof(T)) { case Axis: //...do something break; } return null; }Estoy recibiendo un error en la línea:
case Axis axis:el error es:
La expresión de tipo 'System.Type' no puede ser manejada por un patrón de tipo 'MyNamespace.Axis'.
Creo que mi pregunta es cómo hago para que se llame al Tipo en la especificación <> para poder activarlo.
Las versiones más recientes de C# no han agregado ninguna función específicamente para activar los valores de Type . Si realmente está intentando cambiar según un tipo genérico, probablemente querrá seguir los patrones recomendados en esas otras publicaciones de SO.
Sin embargo, puede haber mejores enfoques que usar tipos genéricos. El hecho de que intente switch ese tipo implica que hay tipos limitados que espera que use el código al llamar a su método. En ese caso, es mejor que utilice explícitamente diferentes métodos para cada uno de esos tipos.
En vez de:
var axis = GetAxis<Axis>(axisObject); var somethingElse = GetAxis<SomethingElse>(axisObject);Usar:
var axis = GetAxis(axisObject); var somethingElse = GetSomethingElse(axisObject);Su ejemplo no parece estar haciendo esto, pero si lo que realmente está tratando de desconectar es el tipo de objeto pasado , entonces las versiones más nuevas de C# brindan algunas mejores opciones a través de la coincidencia de patrones. Por ejemplo:
public T GetAxis<T>(object axisObject) { switch (axisObject) { case Axis axis: //...do something with `axis` break; case SomethingElse somethingElse: //...do something with `somethingElse` break; } return default; } En este último caso, no me queda claro qué valor tiene el tipo genérico T : es posible que pueda reemplazarlo con un tipo de retorno no genérico.
Cuando se trata de este tipo de cosas suelo recurrir al siguiente diccionario:
private Dictionary<Type, Delegate> _axisCases = new Dictionary<Type, Delegate>();Puedes escribir este tipo de código a su alrededor:
public class MyCode { public MyCode() { this.SetCase<Axis>(o => new Axis()); } private Dictionary<Type, Delegate> _axisCases = new Dictionary<Type, Delegate>(); private void SetCase<T>(Func<object, T> func) { _axisCases[typeof(T)] = func; } public T GetAxis<T>(object axisObject) where T : class { var t = typeof(T); if (_axisCases.ContainsKey(t)) { var func = (Func<object, T>)_axisCases[t]; return func(axisObject); } return null; } }Ahora puedes llamarlo así:
var myCode = new MyCode(); var axis = myCode.GetAxis<Axis>(new object());Este tipo de código es el más flexible. Pero si quiere algo más cercano a una declaración de caso normal