Фасад (шаблон проєктування)
Фаса́д — шаблон проєктування, призначений для об'єднання групи підсистем під один уніфікований інтерфейс, надаючи доступ до них через одну точку входу. Це дозволяє спростити роботу з підсистемами.
Фасад належить до структурних шаблонів проєктування.
Складові шаблону
Класи, з яких складається шаблон можна розділити на 3 частини:
- фасад;
- підсистеми;
- клієнти.
Ролі складових
Фасад
- Визначає певним підсистемам інтерфейс, отже знає кому адресувати запити;
- делегує запити клієнтів потрібним об'єктам підсистеми;
- створює нові методи, котрі об'єднують виклики об'єктів системи і\або додають свою логіку;
- приховує підсистеми;
- зменшує кількість параметрів методів, шляхом попередньої підстановки визначених значень.
Підсистема
- реалізує функціонал, закритий та не видимий для зовнішніх компонентів
- виконує роботу, запитану клієнтом через фасад.
- не зберігає посилання на фасад — це означає що одна підсистема може мати довільну кількість фасадів.
Клієнт
- здійснює запити фасаду;
- не знає про існування підсистем.
Переваги та недоліки
Переваги
- Приховує реалізацію підсистеми від клієнтів, що полегшує використання підсистеми
- Сприяє слабкій взаємодії між підсистемою та її клієнтами. Це дозволяє змінити класи, які включають підсистему, не впливаючи на клієнтів.
- Зменшує компіляційні залежностей у великих програмних системах
- Спрощує системи перенесення на інші платформи, оскільки менш імовірно, що для побудови однієї підсистеми потрібно побудувати всі інші
Недоліки
- Не заважає сучасним клієнтам отримувати доступ до базових класів
- Фасад не додає жодної функції, він просто спрощує інтерфейси
Випадки використання
Фасад використовується у випадках, коли потрібно:
- спростити доступ до складної системи;
- створити рівні доступу до системи;
- додати стійкість до змін підсистем;
- зменшити кількість сильних зв'язків між клієнтом та підсистемою, але залишити доступ до повної функціональності.
Зв'язок з іншими патернами
- Фасад створює новий інтерфейс доступу, адаптер — використовує старий
Реалізація
C++
Приклад реалізації на мові С++
#include <iostream>
#include <string>
using namespace std;
// Абстрактный музикант - не є обов'язковою частиною патерну, введений для спрощення коду
class Musician
{
private:
string name;
public:
Musician(string name)
{
this->name = name;
}
virtual ~Musician() {}
protected:
void output(string text)
{
cout << this->name << " " << text << "." << endl;
}
};
// Конкретні музиканти
struct Vocalist : public Musician
{
Vocalist(string name) : Musician(name) {}
void singCouplet(string coupletNumber)
{
string text = "заспівав куплет №" + coupletNumber;
output(text);
}
void singChorus()
{
output("заспівав приспів");
}
};
struct Guitarist : public Musician
{
Guitarist(string name) : Musician(name) {}
void playCoolOpening()
{
output("починає з крутого виступу");
}
void playCoolRiffs()
{
output("грає круті рифи");
}
void playAnotherCoolRiffs()
{
output("грає інші круті рифи");
}
void playIncrediblyCoolSolo()
{
output("лабає неймовірно круте соло");
}
void playFinalAccord()
{
output("закінчує пісню супер акордом");
}
};
struct Bassist : public Musician
{
Bassist(string name) : Musician(name) {}
void followTheDrums()
{
output("слідкує за барабанами");
}
void changeRhythm(string type)
{
string text = "перейшов на ритм ";
output(text + type);
}
void stopPlaying()
{
output("закінчує грати");
}
};
struct Drummer : public Musician
{
Drummer(string name) : Musician(name) {}
void startPlaying()
{
output("починає грати");
}
void stopPlaying()
{
output("закінчує грати");
}
};
// Фасад — в цьому випадку, рок-група
class BlackSabbath
{
private:
Vocalist* vocalist;
Guitarist* guitarist;
Bassist* bassist;
Drummer* drummer;
public:
BlackSabbath()
{
vocalist = new Vocalist("Оззі Осборн");
guitarist = new Guitarist("Тоні Айоммі");
bassist = new Bassist("Гізер Батлер");
drummer = new Drummer("Біл Уорд");
}
void playCoolSong()
{
guitarist->playCoolOpening();
drummer->startPlaying();
bassist->followTheDrums();
guitarist->playCoolRiffs();
vocalist->singCouplet("1");
bassist->changeRhythm("приспів");
guitarist->playAnotherCoolRiffs();
vocalist->singChorus();
bassist->changeRhythm("куплет");
guitarist->playCoolRiffs();
vocalist->singCouplet("2");
bassist->changeRhythm("приспів");
guitarist->playAnotherCoolRiffs();
vocalist->singChorus();
bassist->changeRhythm("куплет");
guitarist->playIncrediblyCoolSolo();
guitarist->playCoolRiffs();
}
};
void main()
{
BlackSabbath* band = new BlackSabbath();
band->playCoolSong();
}
C#
Приклад реалізації на мові С#
using System;
namespace FacadeExample
{
// Клас клієнта
class Client
{
static void Main(string[] args)
{
//Створюємо екземпляр фасаду - інтерфейс підсистем
Facade facade = new Facade();
facade.CallPaired();
Console.WriteLine("\n\n");
facade.CallUnpaired();
Console.ReadKey();
}
}
// Клас фасаду
class Facade
{
Subsystem1 first;
Subsystem2 second;
Subsystem3 third;
Subsystem4 fourth;
Subsystem5 fifth;
public Facade()
{
this.first = new Subsystem1();
this.second = new Subsystem2();
this.third = new Subsystem3();
this.fourth = new Subsystem4();
this.fifth = new Subsystem5();
}
//Виклик методів з підсистем Subsystem2 та Subsystem4
public void CallPaired()
{
Console.WriteLine("Результати роботи методів підсистем з парним індексом (2,4)\n");
second.Method();
fourth.Method();
}
//Виклик методів з підсистем Subsystem1, Subsystem3 та Subsystem5
public void CallUnpaired()
{
Console.WriteLine("Результати роботи методів підсистем з непарним індексом (1,3,5)\n");
first.Method();
third.Method();
fifth.Method();
}
}
// Клас підсистеми
class Subsystem1
{
public void Method()
{
Console.WriteLine("Метод першої підсистеми");
}
}
// Клас підсистеми
class Subsystem2
{
public void Method()
{
Console.WriteLine("Метод другої підсистеми");
}
}
// Клас підсистеми
class Subsystem3
{
public void Method()
{
Console.WriteLine("Метод третьої підсистеми");
}
}
// Клас підсистеми
class Subsystem4
{
public void Method()
{
Console.WriteLine("Метод четвертої підсистеми");
}
}
// Клас підсистеми
class Subsystem5
{
public void Method()
{
Console.WriteLine("Метод п'ятої підсистеми");
}
}
}
This article is issued from Wikipedia. The text is licensed under Creative Commons - Attribution - Sharealike. Additional terms may apply for the media files.