[iOS/Swift] 앱 개발의 실무적 접근 방식으로 배우는 디자인 패턴 ~Composite~

이 기사 시리즈는, iOS/Swift 엔지니어인 집필자 개인이,
매우 일반적인 iOS 앱 개발의 일반적인 상황
Swift의 핵심 라이브러리 및 프레임 워크에서 사용되는 패턴
주목하여 디자인 패턴을 다시 배워 본 기록입니다.

관련 기사 목록
[iOS/Swift] 앱 개발의 실무적 접근 방식으로 배우는 디자인 패턴

Composite 패턴 개요


  • 디렉토리와 파일과 같은 트리 구조를 다루기위한 패턴입니다.
  • 디렉토리와 파일과 같이, 「이름」등의 같은 프로퍼티이나, 「삭제」등의 같은 조작을 가지는 경우, 디렉토리(용기)와 파일(내용)을 똑같이 취급할 수 있습니다.
  • 즉, 검색이나 삭제 등을 재귀적으로 실시할 수 있습니다.
  • GoF 디자인 패턴은 구조와 관련된 패턴으로 분류됩니다.

  • 사용소


  • 그 자체 즈바리, 트리 구조를 취급하는 경우에는, Composite 패턴을 떠올리면 설계에 걸리는 시간을 단축할 가능성이 높습니다.
  • UIView의 View Hierarchy도 트리 구조이며 Composite 패턴을 사용합니다.


  • 인용구 : Cocoa Design Patterns (Retired Document)

    샘플 코드



    Swift 버전은 5.1입니다.
    protocol DirectoryEntry {
        var name: String { get }
        func remove()
    }
    
    final class File: DirectoryEntry {
        let name: String
    
        init(name: String) {
            self.name = name
        }
    
        func remove() {
            print("\(name)を削除しました")
        }
    }
    
    final class Directory: DirectoryEntry {
        let name: String
        private var entryList = [DirectoryEntry]()
    
        init(name: String) {
            self.name = name
        }
    
        func add(entry: DirectoryEntry) {
            entryList.append(entry)
        }
    
        func remove() {
            for entry in entryList {
                entry.remove()
            }
            print("\(name)を削除しました")
        }
    }
    
    // Usage
    let dir1 = Directory(name: "dir1")
    let file1 = File(name: "file1")
    dir1.add(entry: file1)
    // dir1
    //   ∟file1
    
    let dir2 = Directory(name: "dir2")
    let file2 = File(name: "file2")
    let file3 = File(name: "file3")
    dir2.add(entry: file2)
    dir2.add(entry: file3)
    // dir2
    //   ∟file2
    //   ∟file3
    
    dir1.add(entry: dir2)
    // dir1
    //   ∟file1
    //   ∟dir2
    //     ∟file2
    //     ∟file3
    
    let file4 = File(name: "file4")
    dir1.add(entry: file4)
    // dir1
    //   ∟file1
    //   ∟dir2
    //     ∟file2
    //     ∟file3
    //   ∟file4
    
    dir1.remove()
    // "file1を削除しました"
    // "file2を削除しました"
    // "file3を削除しました"
    // "dir2を削除しました"
    // "file4を削除しました"
    // "dir1を削除しました"
    

    좋은 웹페이지 즐겨찾기