Реалізація делегата в Visual C # (Sharp)

Реалізація делегата є простим процесом Потрібно тільки оголосити метод у класі, який має таку ж сигнатуру методу Делегат можна реалізувати за допомогою статичного методу або методу примірника різниці немає ніякої У наступному коді демонструється реалізація делегата ProcessValue на основі обох видів методів,

class Delegatelmplementations  {  void InstanceProcess(int value) { }

static void StaticProcess(int value) { }

public static ProcessValue Staticlnstantiate() { return new ProcessValue(StaticProcess)

}

public ProcessValue Instancelnstantiate() { return new ProcessValue(InstanceProcess)

}

}

У прикладі методи InstanceProcess *) і StaticProcess *) є реалізаціями делегата ProcessValue Делегат не має жодних асоціацій При реалізації мода інтерфейсу класу ми знаємо, які методи яким інтерфейсам належать

З делегатами такого везіння у нас немає Якщо у нас є два делегата з однаковий сигнатурами параметрів і повертається типу, тоді метод з такою ж сіатурой можна використовувати для визначення будь-якого делегата

Щоб методи розпізнавалися як делегати, необхідно поглянути на методи Staticlnstantiate () і Instancelnstantiate () Кожен метод створює екземпляр делегата за допомогою ключового слова new, і кожен екземпляр має один паретр конструктора, який є методом, який потрібно асоціювати з примірниках делегата Зверніть увагу на те, яким чином метод staticlnstantiate про створює екземпляр делегата з методом staticProcess () Це можливо тому, що обидва методи є статичними Так як статичні методи перетворяться в делегати, не грає ролі, скільки разів створюється екземпляр делегата – кожен раз викликається один і той же примірник методу

У реалізації методу instancelnstantiate *) створюється делегат, який служить обгорткою для методу instanceProcess () З першого погляду може здатися, що поведінка е методо в Instancelnstantiate () і Statelnstantiate () Подібні, але між – ду цими двома способами створення екземпляра існує велика різниця А саме, щоб виконати метод instancelnstantiate), Необхідно створити екземпляр Delegate implementations Це дуже важливий аспект, який потрібно брати до уваги Розглянемо наступний початковий код, в якому викорис примірник Delegatelmplemen tat ions,

public ProcessValue GetMeADelegate() {  Delegatelmplementations els = new Delegatelmplementations()

return elsInstancelnstantiate()

}

У реалізації GetMeADelegate () створюється екземпляр класу Delegatelmplementations і викликається метод instancelnstantiate о Так як область видимості обєкта els обмежена методом GetMeADelegate *), може здатися, що збірка сміття для цього обєкта виконується після завершення виконання методу Але це не так При виклику методу instancelnstantiate) Створюється екземпляр делегата, корий посилається на метод instanceProcess <). Тому, хоча делегат посилається на метод, на екземпляр класу els існує посилання, що перешкоджає виконанню збірки сміття для нього.

ПРИМІТКА

Практичним правилом щодо делегатів буде, що якщо делегат посилається на метод примірника, то делегат також посилається на обєкт, тому дл я даного обкта не можна виконувати збірку сміття

Тепер подивимося, як можна реалізувати делегати у прикладі з обчисленням тущей суми і максимального значення:

static class Tests {  static int „runningTotal

static void ProcessRunningTotal(int value) {

_runningTotal += value

}

static int _maxValue

static void ProcessMaximumValue(int value) { if (value &gt _maxValue) {

_maxValue = value

}

}

}

Методи ProcessRunningTotal () і ProcessMaximumValue () мають одну І ту ж сигнатуру ProcessValue (), тому є кандидатами на створення делегатів У кожній реалізації делегата обчислюється поточна сума або нахітся максимальне значення декількох значень Код з використанням делати виглядає так:

static void DoRunningTotalAndMaximum() { List&ltint&gt 1st = new List&ltint&gt { 1, 2, 3, 4 }

_runningTotal = 0

1stIterate(new ProcessValue(ProcessRunningTotal)) ConsoleWriteLine(&quotRunning total is (&quot + _runningTotal + &quot)&quot)

_maxValue = intMinValue

1stIterate(new ProcessValue(ProcessMaximumValue)) ConsoleWriteLine(&quotMaximum value is (&quot + _maxValue + &quot)&quot)

}

У приклад е метод DoRunningTotalAndMaximum *) створює екземпляр класу 1st І присвоює йому значення, використовуючи нотацію ініціалізатора обєкта Потім для обробки в циклі окремих елементів викликається метод 1st iterate про з делати для методу ProcessRunningTotal О Після обчислення і виведення на екран суми значень, знаходиться і виводиться на екран максимальне значення

Рішення із застосуванням делегатів є більш компактним, ніж попереднє рішення із застосуванням абстрактного базового класу Великою перевагою делегатів є надана ними можливість вирішити проблему кодом меншого обсягу, який можна розробити по частинах Реалізація делегатів не представляє ніяких труднощів, як і їх використання

Джерело: Гросс К С # 2008: Пер з англ – СПб: БХВ-Петербург, 2009 – 576 е: ил – (Самовчитель)

Схожі статті:


Сподобалася стаття? Ви можете залишити відгук або підписатися на RSS , щоб автоматично отримувати інформацію про нові статтях.

Коментарів поки що немає.

Ваш отзыв

Поділ на параграфи відбувається автоматично, адреса електронної пошти ніколи не буде опублікований, допустимий HTML: <a href="" title=""> <abbr title=""> <acronym title=""> <b> <blockquote cite=""> <cite> <code> <del datetime=""> <em> <i> <q cite=""> <s> <strike> <strong>

*

*