Они - то же. Каждый более читаем (некоторым), чем другой.
К счастью, .NET 2.0 уже поддерживает дженерики, поэтому вы можете просто создать свой собственный делегат с той же сигнатурой:
public delegate T Func<T>();
Как говорит Конамиман, вы можете очень легко объявить свои собственные типы делегатов. На моей странице "версии" они все объявлены, так что вы можете просто вырезать и вставить их:
public delegate void Action();
public delegate void Action<T1, T2>(T1 arg1, T2 arg2);
public delegate void Action<T1, T2, T3>(T1 arg1, T2 arg2, T3 arg3);
public delegate void Action<T1, T2, T3, T4>(T1 arg1, T2 arg2, T3 arg3, T4 arg4);
public delegate TResult Func<TResult>();
public delegate TResult Func<T, TResult>(T arg);
public delegate TResult Func<T1, T2, TResult>(T1 arg1, T2 arg2);
public delegate TResult Func<T1, T2, T3, TResult>(T1 arg1, T2 arg2, T3 arg3);
public delegate TResult Func<T1, T2, T3, T4, TResult>(T1 arg1, T2 arg2, T3 arg3, T4 arg4);
(я не избегал прокрутки здесь, так как вы, вероятно, не хотите, чтобы разрывы строк в IDE. Обратите внимание, что Action
является частью .NET 2.0, следовательно, его нет выше.)