Шаблоны программирования на Swift: Facade

facade_proSwift

Тема сегодняшней статьи из цикла шаблоны программирования на Swift — шаблон Facade

Facade

Многие сложные системы состоят из огромной кучи компонент. Так же и в жизни, очень часто для совершения одного основного действия, мы должны выполнить много маленьких.

К примеру, чтобы пойти в кино нам надо:

  1. Посмотреть расписание фильмов, выбрать фильм, посмотреть когда есть сеансы, посмотреть когда у нас есть время.

  2. Необходимо купить билет, для этого ввести номер карточки, секретный код, дождаться снятия денег, распечатать билет.
  3. Приехать в кинотеатр, припарковать машину, купить попкорн, найти места, смотреть.

И все это для того, чтобы просто посмотреть фильм, который нам, очень вероятно, не понравится.

Или же возьмем пример Amazon – покупка с одного клика – как много систем задействовано в операции покупки? И проверка Вашей карточки, и проверка Вашего адреса, проверка товара на складе, проверка или возможна доставка даного товара в даную точку мира… В результате очень много действий которые происходят всего по одному клику.

Для таких вот процесов был изобретен паттерн – Фасад ( Facade ) который предоставляет унифицированный интерфейса к большому количеству интерфейсов системы, в следствии чего систему стает гораздо проще в использовании.

Давайте, попробуем создать систему которая нас переносит в другую точку мира с одного нажатия кнопки! Сначала нам нужна система, которая проложит путь от нашего места перебывания в место назначения:

//
// proSwift.ru
//

class Pathfinder {
    func findCurrentLocation() {
        print("Ищем местоположение... О! Вот ты где!")
    }
    
    func findLocationToTravel(location: String) {
        print("Итак, ты хочешь переместиться в \(location)")
    }
    func maeARoute() {
        print("Отлично! Для путешествия будем заглядывать на Яндекс карты...")
    }
}

Так же нам необходима сама система заказа транспорта и собственно путешествия:

//
// proSwift.ru
//

class TravelEngene {
    func findTransport() {
        print("Для путешествия нужны ездовые собаки")
    }
    
    func orderTransport() {
        print("Дайте вот тех, которые в упряжке...")
    }
    func travel() {
        print("Ю-ху! В путь!")
    }
}

Ну и какие же путешествия без билетика:

//
// proSwift.ru
//

class TicketPrintingSystem {
    func createTicket() {
        print("Ожидание ответа от базы...")
    }
    
    func printTicket() {
        print("Ответ получен! На собаках? Не забудь покормить их...")
    }
}

А теперь, давайте создадим единый доступ ко всем этим системам:

//
// proSwift.ru
//

class TravelSystemFacade {
    func travelTo(aLocation: String) {

        let pf = Pathfinder()
        let te = TravelEngene()
        let tp = TicketPrintingSystem()
        
        pf.findCurrentLocation()
        pf.findLocationToTravel(aLocation)
        pf.maeARoute()
        
        te.findTransport()
        te.orderTransport()
        tp.createTicket()
        tp.printTicket()
        te.travel()
    }
}

Фасад знает все про все системы, потому в одном методе он берет и транспортирует нас куда следует. Код теста элементарен:

//
// proSwift.ru
//

let facade = TravelSystemFacade()
facade.travelTo("Лондон")

Консоль отобразит весь процесс путешествия, которое мы вызвали одним методом нашего фасада.

Ищем местоположение... О! Вот ты где!
Итак, ты хочешь переместиться в Лондон
Отлично! Для путешествия будем заглядывать на Яндекс карты...
Для путешествия нужны ездовые собаки
Дайте вот тех, которые в упряжке...
Ожидание ответа от базы...
Ответ получен! На собаках? Не забудь покормить их...
Ю-ху! В путь!

Пример с GitHub

Еще раз:

Шаблон фасад используется для определения простого интерфейса к более сложной подсистеме.

//
// proSwift.ru
//
// https://github.com/ochococo/Design-Patterns-In-Swift/blob/master/source/structural/facade.swift

enum Eternal {
    
    static func setObject(value: AnyObject!, forKey defaultName: String!) {
        let defaults:NSUserDefaults = NSUserDefaults.standardUserDefaults()
        defaults.setObject(value, forKey:defaultName)
        defaults.synchronize()
    }
    
    static func objectForKey(defaultName: String!) -> AnyObject! {
        let defaults:NSUserDefaults = NSUserDefaults.standardUserDefaults()
        
        return defaults.objectForKey(defaultName)
    }
    
}


Eternal.setObject("Disconnect me. I’d rather be nothing", forKey:"Bishop")
Eternal.objectForKey("Bishop")

Шаблоном программирования Фасад определены два метода для записи объектов по ключу в  NSUserDefaults и их получении. Громоздкий код заменяется одной строкой.

2 Comments on “Шаблоны программирования на Swift: Facade

  1. Скажите пожалуйста, почему вы используете enum для Eternal а не допустим class или struct?

    • Я думаю, что в данном конкретном случае программист использовал enum потому что мог. Дело в том, что в очень не большом количестве языков программирования есть возможность добавлять полноценные методы к перечислениям.
      А если обратится к теории, то картина следующая:
      Enum: перечисления представляют собой конечное число «состояний бытия» (случаев). Перечисления инициализируются случаем (кейсом перечисления) и эти случаи всегда должны быть действительными экземплярами.
      Structs следует использовать, когда не существует конечного числа действительных экземпляров, которые также не образуют полного определения объекта
      Классы полностью определяют первичный параметры объекта в вашей модели, ее атрибуты и методы внутреннего и внешнего взаимодействия.

Добавить комментарий

Ваш адрес email не будет опубликован.

*

Этот сайт использует Akismet для борьбы со спамом. Узнайте, как обрабатываются ваши данные комментариев.