Se si dovesse abbandonare l'esigenza di non utilizzare il riflesso, è possibile farlo utilizzando una piccola deviazione.
public class Tester
{
private static readonly MethodInfo _run2Method = typeof(Tester).GetMethod("Run2");
public void Run1<T>()
{
if (typeof(IEnumerable).IsAssignableFrom(typeof(T)))
Run2AsIEnumerable<T>();
else
Console.WriteLine("Run1 for {0}", typeof(T));
}
public void Run2<T>() where T : IEnumerable
{
Console.WriteLine("Run2 for {0}", typeof(T));
}
private void Run2AsIEnumerable<T>()
{
Console.WriteLine("Detour to run2 for {0}", typeof(T));
var method = _run2Method.MakeGenericMethod(typeof(T));
method.Invoke(this, new object[0]);
}
}
Si noti che questo potrebbe essere reso un po 'più efficiente costruendo e memorizzando nella cache i delegati per tipi specifici su richiesta.
L'uscita di questo:
new Tester().Run1<IEnumerable<int>>();
è:
Detour to run2 for System.Collections.Generic.IEnumerable`1[System.Int32]
Run2 for System.Collections.Generic.IEnumerable`1[System.Int32]
Con un po 'di riflessione, sembra che non è così difficile. – Alex
@Alex: Sì, si può fare con la riflessione - ma l'OP chiedeva specificatamente una soluzione senza usare la riflessione. –
Oops, non ho letto abbastanza bene la domanda – Alex