apple/DesignPattern, Architecture
Swift 디자인패턴 Memento Pattern (메멘토 패턴)
lgvv
2022. 4. 13. 19:26
Swift 디자인패턴 Memento Pattern (메멘토 패턴)
Memento 패턴은 객체의 내부 상태를 캡처해서, 이후 해당 상태를 복원할 수 있도록 하는 행동 패턴.
객체의 데이터를 저장하고 복원해야 하는 상황에서 유용
히스토리
- 2022-04-13: 디자인 패턴 스터디 정리
- 2024-11-29: 포스팅 글 재정리 및 조금 더 실용적인 예제 코드로 변경
Memento Pattern
메멘토 패턴은 일반적으로 3개지 개념으로 구성됨
- Originator: 상태를 생성하고, Memento 객체로 저장하거나 복원하는 역할
- Caretaker: Memento 객체를 관리하며, Originator의 상태를 저장하고 복원할 책임을 가짐.
- Memento: Originator의 상태를 저장하는 객체며, 캡슐화를 통해 Originator 외부에서 직접 수정할 수 없게 설계.
메멘토 패턴 장점
- 객체의 상태를 쉽게 복원할 수 있어 Undo / Redo 기능 구현에 적합
- Originator와 Memento 간의 캡슐화를 통해 외부에서 상태를 직접 조작할 위험성을 줄임
메멘토 패턴 단점
- 상태를 저장하는 과정에서 메모리 사용량 증가할 수 있음
- Originator의 상태가 복잡할 경우 Memento 객체 관리가 어려워질 수 있음
코드 예제
게임상태 만들고 저장하고 복구하는 로직 구현
import SwiftUI
// MARK: - Memento
struct GameState {
let level: Int
let score: Int
}
// MARK: - Originator
class Game {
private var level: Int = 1
private var score: Int = 0
func play(level: Int, score: Int) {
self.level = level
self.score = score
print("Playing game: Level \(level), Score \(score)")
}
func saveState() -> GameState {
print("Saving state: Level \(level), Score \(score)")
return GameState(level: level, score: score)
}
func restoreState(_ memento: GameState) {
self.level = memento.level
self.score = memento.score
print("Restored state: Level \(level), Score \(score)")
}
}
// MARK: - Caretaker
class GameSaver {
private var states: [GameState] = []
func save(_ state: GameState) {
states.append(state)
}
func restore() -> GameState? {
guard !states.isEmpty else { return nil }
return states.removeLast()
}
}
private struct ContentView: View {
var body: some View {
Button("Execute") {
// MARK: - Example Usage
let game = Game()
let saver = GameSaver()
// 플레이하고 상태 저장
game.play(level: 1, score: 100)
saver.save(game.saveState())
game.play(level: 2, score: 300)
saver.save(game.saveState())
// 이전 상태로 복원
if let previousState = saver.restore() {
game.restoreState(previousState)
}
if let initialState = saver.restore() {
game.restoreState(initialState)
}
}
}
}
#Preview {
ContentView()
}
(참고)
https://www.raywenderlich.com/books/design-patterns-by-tutorials/v3.0/chapters/7-memento-pattern
https://refactoring.guru/ko/design-patterns/memento