Передача объекта Delegate в метод с помощью Func < > параметр
-
22-07-2019 - |
Вопрос
У меня есть метод Foo4, который принимает параметр типа Func < > ;. Если я передаю параметр анонимного типа, я не получаю ошибки. Но если я создаю и передаю объект типа «делегат», который ссылается на метод с правильной подписью, я получаю ошибку компилятора. Я не могу понять, почему я получаю ошибку в этом случае. Р>
class Learn6
{
delegate string Mydelegate(int a);
public void Start()
{
Mydelegate objMydelegate = new Mydelegate(Foo1);
//No Error
Foo4(delegate(int s) { return s.ToString(); });
//This line gives compiler error.
Foo4(objMydelegate);
}
public string Foo1(int a) { return a.ToString();}
public void Foo4(Func<int, string> F) { Console.WriteLine(F(42)); }
}
Решение
Это работает, если вы передаете ссылку на метод напрямую:
Foo4(Foo1);
Это связано с тем, что фактические делегаты с одинаковой формой изначально не считаются совместимыми. Если контракты неявные, компилятор выводит контракт и сопоставляет их. Если они явные (например, объявленные типы), никакой вывод не выполняется - это просто разные типы.
Это похоже на:
public class Foo
{
public string Property {get;set;}
}
public class Bar
{
public string Property {get;set;}
}
Мы видим, что два класса имеют одинаковую сигнатуру и являются "совместимыми", но компилятор видит их как два разных типа, и ничего более.
Другие советы
Поскольку Func < int, string >
и MyDelegate
- это разные объявленные типы. Они оказываются совместимыми с одним и тем же набором методов; но между ними нет явного преобразования.
//This line gives compiler error.
Foo4(objMydelegate);
//This works ok.
Foo4(objMydelegate.Invoke);
зависит от сценария, но в общем случае нет смысла ограничивать тип Mydelegate, просто используйте Func < int, string > везде :)