События.
Объектно-ориентированное программирование
В данном примере в классе ClassWithEvent описан делегат MyHandler, сигнатура которого содержит три параметра. Событие MyEvent в классе ClassWithEvents является экземпляром класса, заданного делегатом. Инициировать в нужный момент событие, передав обработчику необходимые для его работы параметры (т. е. некоторым способом уведомить клиентов класса, что у него произошло событие). Присоединить… Читать ещё >
События. Объектно-ориентированное программирование (реферат, курсовая, диплом, контрольная)
С помощью делегатов в классах можно описывать события. События — это способ взаимодействия между объектами разных классов. Объекты одного класса могут использовать объекты других классов. Для этого они создают объекты требуемого класса и вызывают его методы (передают ему сообщения). При работе вызванных методов часто возникает необходимость передать сообщения о возникших ситуациях (важных изменениях в своей работе) объектам вызывающего класса, без завершения их работы. Для передачи таких сообщений и используются специальные элементы класса — события.
Класс, которому требуется сообщать о возникновении некоторых ситуаций — событий, должен уметь делать следующее:
- • объявить тип делегата, соответствующего событию;
- • объявить событие в классе (экземпляр делегата);
- • инициировать в нужный момент событие, передав обработчику необходимые для его работы параметры (т. е. некоторым способом уведомить клиентов класса, что у него произошло событие).
Инициируя событие, класс посылает сообщение получателям события — объектам некоторых других классов. Класс, инициирующий событие, называется отправителем сообщения (sender). Классы, чьи объекты получают сообщения, называют классами-получателями сообщении (receiver). Класс-отправитель сообщения в принципе не знает своих получателей. Он просто инициирует событие. Одно и то же сообщение может быть получено и по-разному обработано произвольным числом объектов разных классов.
Интерфейсы и многие классы из библиотеки FCL обладают стандартным набором предопределенных событий.
Объявление события в классе
Сообщение, посылаемое при инициировании события, является аналогом вызова метода. Поскольку сигнатура посылаемого сообщения должна соответствовать сигнатуре принимаемого сообщения, то объявление события синтаксически должно задавать сигнатуру метода.
В C# работа событий реализуется с помощью делегатов. Каждое событие задается делегатом, описывающим сигнатуру метода, который будет обрабатывать сообщения (обработчика события). Объявление события — это двухэтапный процесс:
• Вначале объявляется делегат, как это рассматривалось ранее. Объявление делегата описывается в некотором классе. Но часто это объявление находится вне класса в пространстве имен. Например:
public delegate ([параметры]);
• Если делегат определен, то в классе, создающем события, достаточно объявить событие как экземпляр соответствующего делегата. При этом используется ключевое слово event (это гарантирует, что экземпляр события не может быть вызван в других классах). Объявление события выполняется следующим образом:
public event ;
Ниже приведен пример объявления делегата и события, представляющего экземпляр этого делегата:
// Объявление делегата — новый тип данных public delegate void MyHandler (object о, int n);
// Объявление события класса — экземпляр делегата public event MyHandler MyEvent;
Для инициирования события требуется просто вызвать на выполнение экземпляр делегата. Например:
// проверка, что для события заданы обработчики if (MyEvent ≠ null) MyEvent (this, i); // запускаем событие Ниже приведен пример описания класса, в котором содержится метод, выполнение которого занимает достаточно долгое время. Данный метод сообщает о выполнении каждой десятой доли своей работы. Объекты, использующие данный метод, могут визуально информировать пользователей о ходе выполнения работы в данном методе:
// Объявление нового типа — делегата с параметрами:
// о — ссылка на объект, который инициировал событие.
// п — процент выполненной работы.
public delegate void MyHandler (object о, int n);
// объявление класса с событием.
public class ClassWithEvent {// класс с событием.
// Создание экземпляра делегата — событие.
public event MyHandler MyEvent;
// поле класса private int Volume = 0;
// конструктор класса — параметр — объем работы public EventClass (int p){if (р > 0) Volume = р;}.
//описание метода выполняющего долгую работу.
//(но в данном примере бессмысленную).
public void LongWork () {.
double s = 0; int k = 0;
int st = Volume /10; // десятая часть работы.
for (int i = 0; i < Volume; i++) {.
s += Math. Atan (Math.Sqrt (i) * Math. Sqrt (i)); if (k == st) {// выполнена заданная часть работы if (MyEvent ≠ null) {.
int n = (int)(i*100.0)/Volume;
MyEvent (this, n); // запускаем событие.
}.
k = 0;
}.
else k += 1;
}.
}.
}.
В данном примере в классе ClassWithEvent описан делегат MyHandler, сигнатура которого содержит три параметра. Событие MyEvent в классе ClassWithEvents является экземпляром класса, заданного делегатом.
Обработка событий в классах
Класс, который заинтересован в обработке событий, должен:
- • иметь обработчик события — метод, согласованный по сигнатуре с сигнатурой делегата, который задает событие;
- • иметь ссылку на объект, создающий событие, чтобы получить доступ к этому событию — event-объекту;
- • присоединить обработчик события к event-объекту. Это реализуется с использованием операции += для описанного события.
Пример класса, использующего описанный ранее класс ClassWithEvent с событием, показан ниже:
class Program {.
const int WorkVolume = 10 000 000; // объем работы public static void Main (){.
// создается объект.
ClassWithEvent obj=new ClassWithEvent (WorkVolume); // задается обработчик события.
obj.MyEvent += new MyHandler (ShowStar);
// запускаем длинную работу у объекта, а obj. LongWork ();
// ждем нажатия клавиши Console. ReadLine ();
}.
// обработчик события.
private static void ShowStar (object о, int n) {.
Console.WriteLine («Выполнено {0}%», n);
//Console.Write («*»); // можно просто выводить *.
}.
}.