В чем разница между Func <string, string> и delegate?
Я вижу делегатов в двух формах:
A. Func<string, string> convertMethod = lambda
B. public delegate string convertMethod(string value);
Я не уверен, что на самом деле разница между этими двумя. Они оба делегаты? Я считаю, что первый из них будет использовать лямбда, а второй должен будет иметь метод для фактической работы. Я тоже могу быть смущен.
Ответы
Ответ 1
Прежде всего, ваши два примера делают две совершенно разные вещи. Первый объявляет общую переменную делегата и присваивает ей значение, второе - просто определяет тип delegate
. Ваш пример, более полный, будет:
public static class Program
{
// you can define your own delegate for a nice meaningful name, but the
// generic delegates (Func, Action, Predicate) are all defined already
public delegate string ConvertedMethod(string value);
public static void Main()
{
// both work fine for taking methods, lambdas, etc.
Func<string, string> convertedMethod = s => s + ", Hello!";
ConvertedMethod convertedMethod2 = s => s + ", Hello!";
}
}
Но более того, как Func<string,string>
, так и delegate string convertMethod(string)
могли бы поддерживать одни и те же определения методов, будь то методы, анонимные методы или лямбда-выражения.
Как вам следует использовать, зависит от ситуации. Если вы хотите, чтобы ваш делегат был определен больше по тому, что он принимает и возвращает, то общие делегаты идеальны. Если вы хотите, чтобы у делегата было какое-то особое имя, которое дает больше определений того, что должен делать этот делегат (помимо простых Action
, Predicate
и т.д.), Тогда создание собственного делегата всегда является опцией.
Ответ 2
От MSDN,
В версиях С# до 2.0 единственным способом объявления делегата был для использования названных методов. С# 2.0 представил анонимные методы и в С# 3.0 и более поздние, лямбда-выражения заменяют анонимные методы как предпочтительный способ записи встроенного кода.
и
Существует один случай, когда анонимный метод обеспечивает функциональность не найдено в лямбда-выражениях. Анонимные методы позволяют вам опустить список параметров. Это означает, что анонимный метод может быть преобразуется в делегаты с различными сигнатурами.
Вы также можете быть заинтересованы в этом ответе SO на делегировании ключевого слова vs lambda expression.
Кроме того, MSDN имеет хорошую статью о выражениях лямбда:
delegate int del(int i);
static void Main(string[] args)
{
del myDelegate = x => x * x;
int j = myDelegate(5); //j = 25
}
В предыдущем примере обратите внимание, что подпись делегата имеет один неявно введенный входной параметр типа int и возвращает int. lambda выражение может быть преобразовано в делегат этого типа, потому что он также имеет один входной параметр (x) и возвращаемое значение, которое компилятор может неявно преобразовывать в тип int. (Тип вывода более подробно обсуждается в следующих разделах.) Когда делегат вызывается с использованием входного параметра 5, он возвращает результат 25.
Ответ 3
Образец кода, который у вас есть, немного путает вещи, поэтому позвольте мне попробовать и очистить его. Следующие два элемента - объявления делегатов. Их легко заметить, поскольку они всегда будут содержать ключевое слово delegate
public delegate TReturn Func<TArg, TReturn>(Targ value);
public delegate string convertMethod(string value);
Эта строка кода присваивает значение локальному, которое набирается делегату
Func<string, string> local = lambda;
Приведенный выше код не ограничивается использованием только лямбда. Значение также может быть совместимой группой методов или другим значением делегата.
Еще один пункт, который нужно отметить, состоит в том, что даже если Func<string, string>
и convertMethod
являются делегатами с одинаковыми сигнатурами, их значения не конвертируются друг в друга. Например, незаконно
Func<string, string> local1 = ...;
convertMethod local2 = local1; // Error!!!
Ответ 4
A инициализирует экземпляр делегата (который можно вызвать сразу). Это переменная типа Func < строка, строкa > .
B указывает определение делегата (его подпись). Он может использоваться для определения переменных типа convertMethod.