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

Стратегія (англ. Strategy) — шаблон проєктування, належить до класу шаблонів поведінки. Відомий ще під іншою назвою — «Policy». Його суть полягає у тому, щоб створити декілька схем поведінки для одного об'єкту та винести в окремий клас. Шаблон Стратегія (Strategy) дозволяє міняти вибраний алгоритм незалежно від об'єктів-клієнтів, які його використовують.

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

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

За типом клієнта (або за типом оброблюваних даних) вибрати відповідний алгоритм, який слід застосувати. Якщо використовується правило, яке не піддається змінам, немає необхідності звертатися до шаблону «стратегія».

Структура ред.

 
 

Мотиви ред.

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

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

Відділення процедури вибору алгоритму від його реалізації. Це дозволяє зробити вибір на підставі контексту.

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

  • Клас Strategy визначає, як будуть використовуватися різні алгоритми.
  • Конкретні класи ConcreteStrategy реалізують ці різні алгоритми.
  • Клас Context використовує конкретні класи ConcreteStrategy за допомогою посилання на конкретний тип абстрактного класу Strategy. Класи Strategy і Context взаємодіють з метою реалізації обраного алгоритму (в деяких випадках класу Strategy потрібно надсилати запити класу Context). Клас Context пересилає класу Strategy запит, що надійшов від його класу-клієнта.

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

  • Шаблон Strategy визначає сімейство алгоритмів.
  • Це дозволяє відмовитися від використання перемикачів і / або умовних операторів.
  • Виклик всіх алгоритмів повинен здійснюватися стандартним чином (всі вони повинні мати однаковий інтерфейс).

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

Клас, який використовує алгоритм (Context), включає абстрактний клас (Strategy), що володіє абстрактним методом, визначальним спосіб виклику алгоритму. Кожен похідний клас реалізує один необхідний варіант алгоритму.

Використання ред.

Архітектура Microsoft WDF заснована на цьому патерні. У кожного об'єкта «драйвер» і «пристрій» є незмінна частина, вшита в систему, в якій реєструється змінна частина (стратегія), написана в конкретній реалізації. Змінна частина може бути і зовсім порожньою, що означає, що драйвер нічого не робить, але при цьому здатний брати участь у PnP і управлінні живленням.

Бібліотека ATL містить у собі набір класів threading model, які є стратегіями (різними реалізаціями Lock / Unlock, які потім використовуються основними класами системи). При цьому в цих стратегіях використовується статичний поліморфізм через параметр шаблону, а не динамічний поліморфізм через віртуальні методи.

Призначення шаблону проєктування Стратегія ред.

Існують системи, поведінка яких визначається відповідно до певного роду алгоритмів. Всі вони подібні між собою: призначені для вирішення спільних задач, мають однаковий інтерфейс для користування, але відрізняються тільки «поведінкою», тобто реалізацією. Користувач, налаштувавши програму на потрібний алгоритм — отримує потрібний результат.

Приклад. Є програма(інтерфейс) через яку обраховується ціна на товар для покупців у яких є знижка та ціна за сезонною знижкою — обираємо необхідний алгоритм. Об'єктно-орієнтований дизайн такої програми будується на ідеї використання поліморфізму. Результатом є набір «класів-родичів» — у яких єдиний інтерфейс та різна реалізація алгоритмів.
  • Недоліками такого алгоритму є те, що реалізація жорстко прив'язана до підкласу, що ускладнює внесення змін.
  • Вирішенням даної проблеми є використання патерну Стратегія (Strategy).

Переваги та недоліки ред.

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

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

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

  • Збільшення кількості об'єктів.
  • Клієнт має знати особливості реалізацій стратегій для вибору найбільш вдалої.

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

  • Стратегія змінює реалізацію, декоратор — доповнює
  • В стратегії користувач знає про класи стратегій і міняє їх самостійно, в стані різноманітні стани приховані від користувача, а за їх заміну відповідає сам клас
  • Міст — це структурний патерн. Його компоненти зазвичай встановлюються раз і не змінюються під час виконання програми. Використовують для розділення абстракції та реалізації. Стратегія — це шаблон поведінки. Використовують коли коли алгоритми можуть замінювати один одного під час виконання програми.
  • Шаблонний метод задає кроки алгоритму, які реалізовують підкласи. Стратегія задає алгоритм який можна виконати декількома способами, до того ж вибрати ці способи на етапі виконання програми

Приклади ред.

Приклад на Java ред.

Приклад на C++ ред.

Приклад на C # ред.

Приклади на D ред.

Приклад на Delphi ред.

Приклади на Javascript ред.

Приклад з використанням динамічних (first-class) функцій ред.

Приклади на PHP5

Приклад на Python ред.

Висновки ред.

Останнім часом розроблено багато мов програмування, але в кожній з них для досягнення найкращого результату роботи необхідно використовувати шаблони програмування, одним з яких є Стратегія (Strategy).

Джерела ред.

Design Patterns: Elements of Reusable Object-Oriented Software [Архівовано 9 листопада 2012 у Wayback Machine.]

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

  • Bishop, Judith. C# 3.0 Design Patterns. Sebastopol, California: O'Reilly, 2008.
  • Tomas Petricek, Jon Skeet. Functional Programming for the Real World. б.м.: Manning Publications, 2010.

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