Декоратор (шаблон проєктування)

Декоратор (фр. décorateur) — структурний шаблон проєктування, призначений для динамічного підключення додаткових можливостей до об'єкта. Шаблон Decorator надає гнучку альтернативу методу визначення підкласів з метою розширення функціональності.

Основні характеристики ред.

Завдання ред.

Об'єкт, який передбачається використовувати, виконує основні функції. Проте може виникнути потреба додати до нього деяку додаткову функціональність, яка виконуватиметься до і/або після основної функціональності об'єкта.

Спосіб вирішення ред.

Декоратор передбачає розширення функціональності об'єкта без визначення підкласів.

Учасники ред.

Клас ConcreteComponent — клас, в який за допомогою шаблону Декоратор додається нова функціональність. В деяких випадках базова функціональність надається класами, похідними від класу ConcreteComponent. У подібних випадках клас ConcreteComponent є вже не абстрактним, а конкретним. Абстрактний клас Component визначає інтерфейс для використання всіх цих класів.

Переваги ред.

  • Декоратори забезпечують гнучку альтернативу підкласу для розширення функціональності
  • Декоратори дозволяють модифікувати поведінку під час виконання, а не повертатися до існуючого коду та вносити зміни
  • Декоратори - це хороше рішення для перестановки завдань, тому що ви можете загорнути компонент з будь-якою кількістю декораторів
  • Шаблон декоратора підтримує принцип, що класи повинні бути відкриті для розширення, але закриті для модифікації

Недоліки ред.

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

Наслідки ред.

Функціональність, що додається, реалізується в невеликих об'єктах. Перевага полягає в можливості динамічно додавати цю функціональність до або після основної функціональності об'єкта ConcreteComponent.

Зв'язок з іншими патернами ред.

  • Стратегія змінює реалізацію, декоратор — доповнює
  • Ланцюжок обов’язків та Декоратор виконують операції через серію пов’язаних об’єктів. Але Ланцюжок обов’язків може виконувати довільні дії, незалежні одна від одної, а також у будь-який момент переривати виконання, а декоратори розширюють певну дію, не ламаючи інтерфейс базової операції і не перериваючи виконання інших декораторів.

Реалізація ред.

Створюється абстрактний клас, що представляє як початковий клас, так і нові функції, що додаються в клас. У класах-декораторах нові функції викликаються в необхідній послідовності — до або після виклику подальшого об'єкта.

C++ ред.

C# ред.

Java ред.

Зауваження і коментарі ред.

  • Хоча об'єкт-декоратор може додавати свою функціональність до або після функціональності основного об'єкта, ланцюжок створюваних об'єктів завжди повинен закінчуватися об'єктом класу ConcreteComponent.
  • Базові класи мови Java широко використовують шаблон Декоратор для організації обробки операцій введення-виведення.

Посилання ред.

Література ред.

Алан Шаллоуей, Джеймс Р. Тротт. Шаблоны проектирования. Новый подход к объектно-ориентированному анализу и проектированию = Design Patterns Explained: A New Perspective on Object-Oriented Design. — М. : «Вильямс», 2002. — 288 с. — ISBN 0-201-71594-5.