📖

【学習備忘録】(Swift)Builderパターン

2022/05/16に公開

はじめに

デザインパターンについて、ViewControllerに全て詰め込んでコードを書く方法から脱却したい、そしてTDD(テスト駆動開発)をしたいと思い、まずはデザインパターンの学習をしています。
Builderパターンについて学習し、下の参考リンクの動画内のコードを写経しました。

Builderパターンとは

Builder パターン(ビルダー・パターン)とは、GoF(Gang of Four; 4人のギャングたち)によって定義されたデザインパターンの1つである。 オブジェクトの生成過程を抽象化することによって、動的なオブジェクトの生成を可能にする。
出典: フリー百科事典『ウィキペディア(Wikipedia)

(勝手なイメージですが、同じ材料を使って色々な料理を作ることができるイメージ。)

サンプルコード

・ViewControllerがスッキリしていることに感動しました。
・実際にクラス図を書いたり、コードの流れを追うとより理解が深まりました。

class ViewController: UIViewController {
    let client = Client()

    override func viewDidLoad() {
        super.viewDidLoad()
        print(client.makeText())
        print(client.makeHTML())
    }
}

// Builder
protocol Builder {
    func makeTitle(title: String)
    func makeString(str: String)
    func makeItems(items: [String])
}

//Director
struct Director {
    let builder: Builder

    func construct() {
        builder.makeTitle(title: "Greeting")
        builder.makeString(str: "朝から昼にかけて")
        builder.makeItems(items: [
            "おはようございます",
            "こんにちは"
        ])
        builder.makeString(str: "夜に")
        builder.makeItems(items: [
            "こんばんは",
            "おやすみなさい",
            "さようなら"
        ])
    }
}

// ConcreteBuilder
class TextBuilder: Builder {
    private var buffer = ""

    func makeTitle(title: String) {
        buffer.append("[\(title)]")
        buffer.append("[\n]")
    }

    func makeString(str: String) {
        buffer.append("■\(str)\n")
        buffer.append("\n")
    }

    func makeItems(items: [String]) {
        items.forEach {
            buffer.append(" ・\($0)\n")
        }
        buffer.append("\n")
    }

    func getResult() -> String {
        buffer
    }
}

class HTMLBuilder: Builder {
    private var buffer = ""

    func makeTitle(title: String) {
        buffer.append("<html><head><title>\(title)</title></head><body>\n")
        buffer.append("<h1>\(title)</h1>\n")
    }

    func makeString(str: String) {
        buffer.append("<p>\(str)</p>\n")
    }

    func makeItems(items: [String]) {
        buffer.append("<ul>\n")
        items.forEach {
            buffer.append("<li>\($0)</li>\n")
        }
        buffer.append("</ul>\n")
    }

    func getResult() -> String {
        buffer
    }
}

// Client
struct Client {
    func makeText() -> String {
        let textBuilder = TextBuilder()
        let director = Director(builder: textBuilder)
        director.construct()
        return textBuilder.getResult()
    }

    func makeHTML() -> String {
        let htmlBuilder = HTMLBuilder()
        let director = Director(builder: htmlBuilder)
        director.construct()
        return htmlBuilder.getResult()
    }
}

GitHub

https://github.com/MasakatsuTagishi/Practice-BuilderPattern

参考にしたもの

1.[ライブ] Swiftでデザインパターン使ってみる(Adapter, Builder, Strategy)

https://www.youtube.com/watch?v=RU_jsa1MmSk&t=3578s

2.Builder パターン

https://ja.wikipedia.org/wiki/Builder_パターン#:~:text=Builder パターン(ビルダー・パターン),生成を可能にする。

さいごに

写経し、データの流れを追うことでより理解が深まりました。また、書籍のコードやネットのコードを理解する、そして他人のコードを読めるようになるにも、デザインパターンを学習することで助けになってくれると感じました。
間違いや認識違いがあれば指摘いただければ幸いです。

Discussion