Поделиться через


События и делегаты

Обновлен: Ноябрь 2007

Событие представляет собой сообщение, посылаемое объектом, чтобы сигнализировать о совершении какого-либо действия. Это действие может быть вызвано в результате взаимодействия с пользователем, например при нажатии кнопки мыши, или может быть обусловлено логикой работы программы. Объект, вызывающий событие, называется отправителем события. Объект, который захватывает событие и реагирует на него, называется получателем события.

При обмене событиями классу отправителя событий не известен объект или метод, который будет получать (обрабатывать) сформированные отправителем события. Необходимо, чтобы между источником и получателем события имелся посредник (или механизм подобный указателю). .NET Framework определяет специальный тип (Delegate), обеспечивающий функциональные возможности указателя функции.

Делегат является классом, который может хранить ссылку на метод. В отличие от других классов класс делегата имеет подпись и может хранить ссылки только на методы, соответствующие этой подписи. Таким образом, делегат эквивалентен строго типизированному указателю функции или обратному вызову. Хотя делегаты имеют и другие направления использования, здесь будут рассматриваться только функциональные возможности делегатов по обработке событий. Объявление делегата является достаточным для определения класса делегата. Объявление предоставляет подпись делегата, а среда CLR обеспечивает реализацию. В следующем примере показан порядок объявления делегата событий.

public delegate void AlarmEventHandler(object sender, AlarmEventArgs e);
Public Delegate Sub AlarmEventHandler(sender As Object, e As AlarmEventArgs)

Синтаксис сходен с синтаксисом объявления метода. Однако зарезервированное слово delegate сообщает компилятору, что AlarmEventHandler является типом делегата. По соглашению делегаты событий в .NET Framework имеют два параметра: источник, вызвавший событие, и данные для события.

Экземпляр делегата AlarmEventHandler можно привязать к любому методу, который соответствует его подписи, такому как метод AlarmRang класса WakeMeUp, как показано в следующем примере.

public class WakeMeUp 
{
    // AlarmRang has the same signature as AlarmEventHandler.
    public void AlarmRang(object sender, AlarmEventArgs e)
    {...};
    ...
}
Public Class WakeMeUp
   ' AlarmRang has the same signature as AlarmEventHandler.
   Public Sub AlarmRang(sender As Object, e As AlarmEventArgs)
      ...
   End Sub
   ...
End Class

Пользовательские делегаты событий необходимы только в случаях, когда событие создает данные для события. Многие события, включая некоторые события пользовательского интерфейса, например щелчки мышью, не создают данных для события. В таких ситуациях делегат события, предоставляемый библиотекой классов для события без данных, System.EventHandler является целесообразным. Его объявление приводится ниже.

delegate void EventHandler(object sender, EventArgs e);
Public Delegate Sub EventHandler(sender As Object, e As EventArgs)

Делегаты событий являются многоадресными. Это означает, что они могут хранить ссылки на несколько методов обработки событий. Дополнительные сведения см. в разделе Delegate. Делегаты позволяют осуществлять гибкий и детальный контроль при обработке событий. Делегат действует как диспетчер событий для класса, вызвавшего событие, обслуживая для события список зарегистрированных обработчиков событий.

Сведения об использовании делегатов для предоставления функциональных возможностей событий в компоненте или элементе управления содержатся в разделе Создание событий.

Общие сведения о потреблении событий в приложениях содержатся в разделе Потребление событий.

См. также

Задачи

Практическое руководство. Вызов и прием событий

Практическое руководство. Соединение методов обработчика событий с событиями

Основные понятия

Прием событий

Вызов события

Другие ресурсы

Обработка и вызов событий