Полиморфные делегаты - PullRequest
5 голосов
/ 06 октября 2010

C # включается

delegate void Bar<T>(T t);

void foo(Bar bar)
{
    bar.Invoke("hello");
    bar.Invoke(42);
}

Обходной путь должен использовать интерфейс

interface Bar
{
    void Invoke<T>(T t);
}

но теперь мне нужно изо всех сил, чтобы определить реализации интерфейса. Могу ли я добиться того же с делегатами и простыми методами?

Ответы [ 3 ]

5 голосов
/ 06 октября 2010

Это невозможно, поскольку вы не можете назначить открытый универсальный метод делегату.Было бы интересно предложить новую функцию, но в настоящее время C # не допускает этого.

Возможные обходные пути:

delegate void Bar(object t);

void foo(Bar bar)
{
    bar.Invoke("hello");
    bar.Invoke(42);
}

void BarMethod(object t)
{
    if (t is int)
        // ...
    else if (t is string)
        // ...
}

foo(BarMethod);

delegate void Bar<T>(T t);

void foo(Bar<string> stringBar, Bar<int> intBar)
{
    stringBar.Invoke("hello");
    intBar.Invoke(42);
}

void BarMethod<T>(T t)
{
    // ...
}

foo(BarMethod<string>, BarMethod<int>);

Обходной путь интерфейса, о котором вы уже упоминали:

interface IBar
{
    void Invoke<T>(T t);
}

void foo(IBar bar)
{
    bar.Invoke("hello");
    bar.Invoke(42);
}

class BarType : IBar
{
    public void Invoke<T>(T t)
    {
        // ...
    }
}

foo(new BarType());
0 голосов
/ 06 октября 2010

Я вижу некоторую полезность, например, наличие подпрограмма "SerializeSomething (вещь как T)", у которой был бы тип, который она могла бы передать другим родовым типам. К сожалению, я думаю, что такой делегат должен был бы иметь некоторую дополнительную информацию о типах, связанную с этим, чтобы заставить такие обобщенные элементы работать. Например, тип T не может быть фактическим типом «вещи». Если «вещь» объявлена ​​как SomeBaseType, но на самом деле является DerivativeOfSomeBaseType, код SerializeSomething (вещь) будет вызывать SerializeSomething (вещь). Я ничего не знаю, означает в механизме делегата, с помощью которого тип SomeBaseType будет передаваться цели делегата.

0 голосов
/ 06 октября 2010

Может быть, ваш пример не совсем иллюстрирует ваше намерение, но какой здесь смысл в дженериках? Вы не используете тип T каким-либо полезным способом, и я бы использовал object вместо T.

Добро пожаловать на сайт PullRequest, где вы можете задавать вопросы и получать ответы от других членов сообщества.
...