Трикове с интерфейси в Delphi
Трик 1. Интелигентни слаби връзки
Слабите референции имат и друга страна. Ако изведнъж вашият обект бъде унищожен и някой държи слаба връзка с него, вие не можете да го проследите. Всъщност вие просто имате указател за боклук, който ще доведе до грешка при достъп. И това е ужасно. Необходимо е да се извае някаква система за почистване на тези връзки.
Трик 2: Механизмът на абоната
Ако все още не сте преминали през системата за плъгини в Delphi и не сте използвали MVC шаблони, значи сте късметлии. В Delphi всички събития са само един или два указателя към функция (и екземпляр). Следователно, ако сте създали клас, направили сте го свойствоOnBlaBla, тогава само един човек може да разбере, че същият тозиBlaBlaнай-накрая се е случил. Следователно всеки започва да вижда своя механизъм за абонамент и често се удавя в отстраняването на грешки в същите тези абонаменти. Базираните на интерфейс събития обикновено се реализират по този начин. Те правят отделен интерфейс за събитие, например: и го предават, вместо класическата процедура на обект; например в двойка методи за абониране / отписване: Когато кодът расте и интерфейсътIMouseEventsсе промени малко (например, беше добавен метод) - рефакторингът започва да се натоварва много. Например, същотоIMouseEventsсе използва вIForm,IButton,IImageи други зли духове. Навсякъде трябва да коригирате правилно абонамента, да добавите байпас от абонати и т.н. Използвам следния трик. Пишем интерфейса: Класът, който ще имплементира този интерфейс (нека бъдеTBasePublisher) може да добавя и премахва само някои интерфейси от списъка. В бъдеще ще пишем класове, които наричам разпространители. Тук имаме интерфейс за събития: Ние наследяваме от TBasePublisher и прилагаме следния разпространител: тоест самият разпространител внедрява интерфейса за събития и ввнедряването просто изпраща едно и също събитие до всички абонати. Предимството е, че всичко е имплементирано на едно място, няма да се компилира, ако променитеIGraphEventsдори малко. Сега зоопаркътIForm,IButton,IImageпросто създаваTGraphEventsBroadcasterвътре в себе си и извиква неговите методи, сякашIFormима само един абонат.
Трик 3. Интелигентни слаби връзки + механизъм за абонати
Но всичко, което описах по-горе за абонатите, е лошо. Факт е, че ще има циклични препратки тук и там, махате да се справите с реда на финализиране и отписване. Ще добавите слаби връзки, но ще затънете в отстраняване на грешки в нежелани връзки. Тук са полезни интелигентните слаби препратки, описани в самото начало. Ние просто пишем следния интерфейс на издателя (който приемаIWeaklyот началото на статията): Вътрешно, TBasePublisher съхранява масив от слаби препратки TWeakRefArr = масив от IWeakRef; И разпространителят сега проверява само слабата референция за жизнеспособност, получава нормалната и изпраща събитието до нея. Излъчвателят се промени по следния начин: Сега изобщо не се интересуваме от реда на отписване. Ако сме забравили да се отпишем, няма проблем. Всичко стана прозрачно, както трябваше да бъде в dotnet.
Трик 4. Претоварването на помощ
Финален щрих: Мисля, че е ясно без думи. Ние просто правимMyForm.MyEvents + MySubscriber; - записахме се. Изваден:MyForm.MyEvents - MySubscriber; - отписан.
Статията няма да е пълна, ако не дам пример за това как работи. Ето един пример. Накратко: Програмата създава 4 прозореца. На всеки от прозорците можете да рисувате с мишката. Начертаните обекти се добавят към списъка и чрез механизма за абонамент всички прозорци се уведомяват за промяната. Следователно, нарисуваната фигурасе появява на всички формуляри. Във всеки формуляр можете да изберете собствена дебелина на линията, като използвате тракбара.
Идеята за слабите връзки е измислена от Дмитрий Илиних от Maxidix s.r.o. и модифициран от мен.
Hardcore conf в C++. Каним само професионалисти.