¿Por qué debo proporcionar tipos de parámetros explícitamente generics mientras que el comstackdor debe inferir el tipo?

¿Por qué debo proporcionar tipos de parámetros explícitamente generics mientras que el comstackdor debe inferir el tipo?

public static T2 Cast(this T1 arg) where T2 : class where T1 : class { return arg as T2; } 

Uso de la muestra:

  objOfTypeT2 = objOfTypeT1.Cast(); 

Comparado con mi uso deseado con un comstackdor más inteligente:

  objOfTypeT2 = objOfTypeT1.Cast(); 

o tal vez debería ser más inteligente 🙂

Tenga cuidado de que proporcione el tipo de devolución . No deseo proporcionar el objeto al que llamé la función, el método es un Método de extensión .

La especificación limita la inferencia de parámetro de tipo para métodos generics a todo o nada. No puedes tener una inferencia parcial.

La lógica probablemente sea simplificar las reglas de inferencia de tipo (que ya son bastante complejas, ya que también deben tener en cuenta las reglas de sobrecarga).

La inferencia no considera el tipo de devolución; sin embargo, puedes intentar dividir los generics; por ejemplo, podría escribir código para permitir:

 .Cast().To() 

teniendo (no probado, solo indicativo)

 public static CastHelper Cast(this T obj) { return new CastHelper(obj); } public struct CastHelper { private readonly TFrom obj; public CastHelper(TFrom obj) { this.obj = obj;} public TTo To() { // your code here } } 

He usado la solución de Marc Gravell y me gusta, pero puedo presentar otra alternativa.

Debido a que los parámetros generics se deducen de los parámetros, otra opción es usar un parámetro de salida para el resultado en lugar de un valor de retorno.

Esto ha sido posible durante mucho tiempo, pero el C # de hoy te permite declarar la variable en línea, que considero que es un flujo utilizable.

 public static void Cast(this T1 arg, out T2 result) where T2 : class where T1 : class { result = arg as T2; } 

Puedes llamar esto de la siguiente manera

 objOfTypeT1.Cast(out Type2 objOfTypeT2);