C # делегат для двух методов с разными параметрами - PullRequest
16 голосов
/ 18 декабря 2008

Я использую следующие методы:

public void M1(Int32 a)
{
  // acquire MyMutex
  DoSomething(a);
  // release MyMutex
}

и

public void M2(String s, String t)
{
  // acquire MyMutex
  DoSomethingElse(s, t);
  // release MyMutex
}

Из того, что я нашел до сих пор, кажется, что невозможно использовать один делегат для двух методов с разными сигнатурами.

Есть ли другие альтернативы, чтобы написать что-то вроде этого:

public void UsingMutex(...)
{
  // acquire MyMutex
  ...
  // release MyMutex
}

UsingMutex(M1);
UsingMutex(M2);

На данный момент я могу думать только о том, чтобы использовать двух делегатов и логический флаг, чтобы знать, какой делегат вызывать, но это не долгосрочное решение.

Можно ли комбинировать дженерики с делегатами? И если да, есть ли у вас ссылки на какую-либо документацию?

Среда: C # 2.0

Ответы [ 3 ]

19 голосов
/ 18 декабря 2008

Абсолютно вы можете смешивать делегатов с генериками. В 2.0, Predicate<T> и т. Д. Являются хорошими примерами этого, но вы должны иметь одинаковое количество аргументов. В этом сценарии, возможно, вариант заключается в использовании перехватов для включения аргументов в делегат?

т.е.

    public delegate void Action();
    static void Main()
    {
        DoStuff(delegate {Foo(5);});
        DoStuff(delegate {Bar("abc","def");});
    }
    static void DoStuff(Action action)
    {
        action();
    }
    static void Foo(int i)
    {
        Console.WriteLine(i);
    }
    static void Bar(string s, string t)
    {
        Console.WriteLine(s+t);
    }

Обратите внимание, что Action определено для вас в .NET 3.5, но вы можете повторно объявить его для целей 2.0; -p

Обратите внимание, что анонимный метод (delegate {...}) также может быть параметризован:

    static void Main()
    {
        DoStuff(delegate (string s) {Foo(5);});
        DoStuff(delegate (string s) {Bar(s,"def");});
    }
    static void DoStuff(Action<string> action)
    {
        action("abc");
    }
    static void Foo(int i)
    {
        Console.WriteLine(i);
    }
    static void Bar(string s, string t)
    {
        Console.WriteLine(s+t);
    }

Наконец, C # 3.0 делает все это намного проще и красивее с "лямбдами", но это уже другая тема; -p

4 голосов
/ 18 декабря 2008

Да, можно объединять дженерики с делегатами.

public delegate void Action<T>(T x);
public delegate void Action<T,U>(T x, U y);

public void UsingMutex<T>(Action<T> x, T t) {
    // acquire mutex...
    x(t);
    // release mutex...
}
public void UsingMutex<T,U>(Action<T,U> x, T t, U u) {
    // acquire mutex...
    x(t, u);
    // release mutex...
}

Но вам все равно придется обрабатывать разное количество параметров с использованием перегрузок.

3 голосов
/ 18 декабря 2008

Если вы посмотрите на делегатов Func<T> и Action<T> в платформе, вы увидите, что они определяют количество похожих делегатов с различным количеством параметров. Вы можете использовать дженерики, но это не решает проблему количества аргументов, о которой вы говорите.

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