티스토리 뷰
Observer(옵저버) - behavioral pattern (행동 패턴)
옵저버 패턴은 여러 개의 객체들이 관찰할 객체를 구독(subscribe)하고 관찰하는 패턴이다.
유튜브 채널 구독과 똑같이 생각하면 편하다.
구독을 하면 채널에 새로운 영상이 올라올 때 구독자들에게 알람이 전송된다.
옵저버 패턴에서도 관찰할 객체 Publisher의 상태가 바뀌면 구독한 객체 Subscriber들이 그 변화를 알게된다.
Publisher
Publisher의 상태가 변하거나 일부 동작을 실행할 경우 관찰하고 있는 객체들 Subscriber에게 알립니다. 구독/구독취소를 하는 subscribe, unsubscribe 메소드를 가지고 있습니다.
Subscriber
Subscriber는 알림(notification) 인터페이스를 정의합니다. 그림에서 보이는 것처럼 대부분의 경우 하나의 업데이트 메소드를 가집니다.
Concrete Subscriber
Concrete Subscriber는 Publisher 가 보낸 알림에 응답하는 동작을 수행합니다. Publisher가 독립적일 수 있도록 동일한 인터페이스를 가져야 합니다.
보통 Subscriber는 주기적인 업데이트를 위해 문맥상의 정보가 필요합니다. 그림에서처럼 Publisher가 context라는 데이터를 전달하고 Subscriber는 이를 통해 업데이트를 진행합니다.
Client
Client는 Publisher와 Subscriber를 각각 생성합니다. Publisher 업데이터를 위해 Subscriber를 등록합니다.
When?
- 다른 객체에 의존하는 여러 개의 객체들이 있을 때
- 한 객체가 다른 객체에서 이벤트가 발생할 때 작업을 수행해야 하는 경우, 이 때 개발자들은 얼마나 많은 객체들이 변경되어야 하는지 몰라도 된다.
- 객체가 자신의 존재를 알리지 않고 알림을 전달할 때
Code
Youtube 채널을 구독하고 구독해제하는 것으로 코드를 작성해보겠다.
우선 Subscirber (=Observer) 를 구현해준다.
protocol Subscriber {
var id:String {get}
func update(youtube: YoutubeChannel)
}
그 다음으로 Publisher의 역할을 하는 YoutubeChannel 클래스를 구현해준다.
Publisher에는 subscribe/unSubscribe 메소드를 구현해주어야 한다.
class YoutubeChannel {
var subscribers:[Subscriber]
init (subscribers: [Subscriber] ) {
self.subscribers = subscribers
}
func subscribe(subscriber: Subscriber ){
self.subscribers.append(subscriber)
}
func unSubscribe(subscriber: Subscriber ){
if let idx = self.subscribers.firstIndex(where: { $0.id == subscriber.id}) {
self.subscribers.remove(at: idx)
}
}
func notifty() {
self.subscribers.forEach({ $0.update(youtube: self)})
}
}
Concrete Subscriber의 역할을 하는 YoutubeSubscriber 클래스를 구현해준다.
class YoutubeSubscriber:Subscriber {
var id:String
init(id: String){
self.id = id
}
func update(youtube: YoutubeChannel) {
print("\(id)님! 새로운 영상이 올라왔어요")
}
}
인스턴스를 생성하고 메소드를 실현해준다.
let iosStudyChannel = YoutubeChannel(subscribers: [])
let malcha = YoutubeSubscriber(id: "Malcha")
let frappuccino = YoutubeSubscriber(id: "frappuccino")
iosStudyChannel.subscribe(subscriber: malcha)
iosStudyChannel.notifty()
malcha만 구독을 했을 경우
malcha와 frappuccino 둘 다 구독했을 경우, 모두 다 알람이 잘 가는 것을 확인할 수 있다.
malcha가 재미없어져서 채널을 구독해제(unSubscribe) 했다.
frappuccino 에게만 알람이 가는 것을 확인할 수 있다.
Result
옵저버 패턴의 장점
1. 객체지향 프로그램의 개방-폐쇄 원칙(Open/Closed Principle)을 준수한다.
2. 런타임 중에 객체 사이의 관계를 만들 수 있다.
구독 / 구독 취소를 통해 런타임 중에 객체 사이의 관계를 조절할 수 있다.
옵저버 패턴의 단점
1. Subscriber가 랜덤 순서로 알림을 받는다.
즉 원하는 순서대로 알림을 보낼 수가 없다.
Swift에서는 Combine을 사용하면 쉽게 옵저버 패턴을 구현할 수 있다. (Swift 짱!) Combine 글 보기
옵저버 패턴 끝!
😊
'Swift > Design Pattern' 카테고리의 다른 글
[Swift Design Pattern 09] MVC (0) | 2022.03.19 |
---|---|
[Swift Design Pattern 07] Template Method (템플릿 메소드) (0) | 2022.03.16 |
[Swift Design Pattern 06] Adapter (어뎁터) (0) | 2022.03.15 |
[Swift Design Pattern 05] Decorator (데코레이터) (1) | 2022.03.12 |
[Swift Design Pattern 04] Facade (퍼사드) (0) | 2022.03.08 |
- Total
- Today
- Yesterday
- 책
- 프로그래머스
- 디자인 패턴
- Swift공식문서
- Combine
- 책리뷰
- Swift 서버
- 책후기
- 필독서
- todo앱
- 부스트캠프iOS
- 애플
- 코딩
- ios
- 코딩테스트
- Swift DocC
- 날씨어플
- TODO
- SwiftUI
- vapor
- Swift 디자인 패턴
- 부스트캠프
- 앱개발
- 코딩 테스트
- swiftUI 기초
- Swift문법
- 부스트캠프7기
- Swift
- 개발
- UX
일 | 월 | 화 | 수 | 목 | 금 | 토 |
---|---|---|---|---|---|---|
1 | 2 | 3 | ||||
4 | 5 | 6 | 7 | 8 | 9 | 10 |
11 | 12 | 13 | 14 | 15 | 16 | 17 |
18 | 19 | 20 | 21 | 22 | 23 | 24 |
25 | 26 | 27 | 28 | 29 | 30 | 31 |