[swift] 데코레이터 패턴
데코레이터 패턴은 객체의 기능을 동적으로 확장하는 패턴 중 하나입니다. 이 패턴은 기존 객체에 새로운 기능을 추가하거나 변경하지 않고, 런타임 시 동적으로 추가 기능을 구현할 수 있습니다.
데코레이터 패턴의 구조
데코레이터 패턴은 크게 컴포넌트(Component), 컨크리트 컴포넌트(Concrete Component), 데코레이터(Decorator), 컨크리트 데코레이터(Concrete Decorator)로 구성됩니다.
- 컴포넌트(Component): 인터페이스 역할을 하며, 기본 동작을 정의합니다.
- 컨크리트 컴포넌트(Concrete Component): 기본 동작을 구현한 클래스로, 실제 객체의 역할을 합니다.
- 데코레이터(Decorator): 컴포넌트의 인터페이스를 유지하면서 추가적인 동작을 정의합니다.
- 컨크리트 데코레이터(Concrete Decorator): 실제로 동작을 추가하는 역할을 하며, 데코레이터를 상속받아 구현합니다.
데코레이터 패턴의 장점
- 기존 코드의 변경이 없음: 기존 코드를 수정하지 않고, 동작을 추가할 수 있습니다.
- 동적으로 적용 가능: 런타임 시 동작을 추가할 수 있어 유연성이 뛰어납니다.
Swift에서의 데코레이터 패턴 구현
protocol Coffee {
func brewing() -> String
}
class SimpleCoffee: Coffee {
func brewing() -> String {
return "커피가 추출됩니다."
}
}
class CoffeeDecorator: Coffee {
private let decoratedCoffee: Coffee
required init(decoratedCoffee: Coffee) {
self.decoratedCoffee = decoratedCoffee
}
func brewing() -> String {
return decoratedCoffee.brewing()
}
}
class MilkDecorator: CoffeeDecorator {
override func brewing() -> String {
return super.brewing() + " 우유가 추가됩니다."
}
}
class SugarDecorator: CoffeeDecorator {
override func brewing() -> String {
return super.brewing() + " 설탕이 추가됩니다."
}
}
let myCoffee: Coffee = SimpleCoffee()
let coffeeWithMilk: Coffee = MilkDecorator(decoratedCoffee: myCoffee)
let coffeeWithMilkAndSugar: Coffee = SugarDecorator(decoratedCoffee: coffeeWithMilk)
print(coffeeWithMilkAndSugar.brewing())
위 코드는 스위프트에서 데코레이터 패턴을 구현한 예시입니다.
결론
데코레이터 패턴은 객체 지향 프로그래밍에서 기존 객체에 유연하게 동작을 추가할 수 있는 패턴으로, 객체간의 결합도를 낮추는데 도움을 줍니다. Swift에서 기능을 동적으로 확장하고 싶을 때, 데코레이터 패턴을 고려해보는 것이 좋습니다.