То, о чем вы здесь говорите, обычно обрабатывается как события в C #, например;
public class SomeType {
public event EventHandler SomeEvent;
protected virtual void OnSomeEvent() {
EventHandler handler = SomeEvent;
if(handler!=null) handler(this,EventArgs.Empty);
}
public void SomethingInteresting() {
// blah
OnSomeEvent(); // notify subscribers
// blap
}
// ...
}
С подписчиками ...
SomeType obj = new SomeType();
//...
obj.SomeEvent += /* some handler */
//...
обработчик может быть методом, но при обсуждении сигнатур и т. Д. Наиболее распространенным способом повторного использования существующих методов с несоответствующими сигнатурами являются анонимные методы:
obj.SomeEvent += delegate { this.Text = "Done!"; };
Вы можете иметь список делегатов:
List<SomeDelegateType> list = new List<SomeDelegateType>();
list.Add(...);
но это может быть избыточно, потому что экземпляры делегатов multicast - так что вы можете сделать это более напрямую:
Action action = null;
action += delegate { Console.WriteLine("Did A");};
action += delegate { Console.WriteLine("Did B");};
action(); // does both A & B
Обратите внимание, что более сложное использование делегата может включать входящие значения аргументов - например:
int i = 24;
Func<int,int,int> func = (x,y) => (x * i) + y;
int result = func(2, 3); // 51
Комбинируя такие вещи, как анонимные методы (или лямбда-выражения, как указано выше) с захваченными переменными, проблема с подписями сигнатур редко встречается - вы можете просто заключить лямбду, чтобы сделать совпадение сигнатуры (добавление дополнительных значений или удаление аргументы, по мере необходимости).
Обратите внимание, что при событиях (в частности) общим подходом является сохранение подписи:
void SomeDelegateType(object sender, SomeArgsType args);
где SomeArgsType : EventArgs
- или используйте EventHandler<T>
, который сделает это за вас.