옵저버패턴이란 객체의 상태 변화를 관찰하는 관찰자(옵저버)들의 목록을 객체에 등록하여 상태 변화가 있을 때마다 객체가 직접 등록된 각각의 옵저버에게 통지하도록 하는 디자인 패턴이다.
ex) 1~N까지 숫자가 증가할 때 해당 숫자가 3의 배수, 5의 배수인 경우 이벤트가 발생된다.
Observer 인터페이스
public interface Observer {
public void update(int number);
}
Subject 인터페이스
public interface Subject {
public void registerObserver(Observer o);
public void removeObserver(Observer o);
public void notifyObservers();
}
Event 인터페이스
public interface ActionEvent {
public void action();
}
Observer들이 상속받는 인터페이스로 다이어그램의 display() 메소드를 구현하기 위함.
Observer 객체
public class Multiple3Counting implements Observer, ActionEvent {
private int number;
private NumberCounting numberCounting;
public Multiple3Counting(NumberCounting numberCounting) {
this.numberCounting = numberCounting;
numberCounting.registerObserver(this);
}
@Override
public void action() {
System.out.println("[3] MultipleCounting number : " + number);
}
@Override
public void update(int number) {
this.number = number;
if(number % 3 == 0) {
action();
}
}
}
public class Multiple5Counting implements Observer, ActionEvent {
private int number;
private NumberCounting numberCounting;
public Multiple5Counting(NumberCounting numberCounting) {
this.numberCounting = numberCounting;
numberCounting.registerObserver(this);
}
@Override
public void action() {
System.out.println("[5] MultipleCounting number : " + number);
}
@Override
public void update(int number) {
this.number = number;
if(number % 5 == 0) {
action();
}
}
}
Subject 객체
public class NumberCounting implements Subject {
private List<Observer> observers;
int number;
public NumberCounting() {
observers = new ArrayList<Observer>();
}
@Override
public void registerObserver(Observer o) {
observers.add(o);
}
@Override
public void removeObserver(Observer o) {
observers.remove(o);
}
@Override
public void notifyObservers() {
for (Observer observer : observers) {
observer.update(number);
}
}
public void numberChanged() {
notifyObservers();
}
public void setNumber(int number) {
this.number = number;
numberChanged();
}
public int getNumber() {
return number;
}
}
Main
public class ObserverMain {
public static void main(String[] args) {
NumberCounting numberCounting = new NumberCounting();
Multiple3Counting multiple3Counting = new Multiple3Counting(numberCounting);
Multiple5Counting multiple5Counting = new Multiple5Counting(numberCounting);
for(int number = 0 ; number <= 10 ; number++) {
numberCounting.setNumber(number);
}
System.out.println("#########removeObserver#########");
numberCounting.removeObserver(multiple5Counting);
for(int number = 0 ; number <= 10 ; number++) {
numberCounting.setNumber(number);
}
}
}
실행결과
[3] MultipleCounting number : 0
[5] MultipleCounting number : 0
[3] MultipleCounting number : 3
[5] MultipleCounting number : 5
[3] MultipleCounting number : 6
[3] MultipleCounting number : 9
[5] MultipleCounting number : 10
#########removeObserver#########
[3] MultipleCounting number : 0
[3] MultipleCounting number : 3
[3] MultipleCounting number : 6
[3] MultipleCounting number : 9
두 객체가 느슨하게 결합되어 있다는 것은, 그 둘이 상호작용을 하긴 하지만 서로에 대해 잘 모르는 것을 의미합니다.
옵저버 패턴에서는 주제와 옵저버가 느슨하게 결합되어 있는 객체 디자인을 제공합니다.
장점
1. 옵저버를 언제든 새로 추가, 제거할 수 있다.
2. 새로운 형식의 옵저버라 할 지라도 주제를 전혀 변경할 필요가 없다.
3. 주제와 옵저버는 서로 독립적으로 재사용할 수 있다.
4. 주제나 옵저버가 바뀌더라도 서로에게 영향을 미치지 않는다.
장점
1. 실시간으로 한 객체의 변경사항을 다른 객체에 전파할 수 있습니다.
2. 느슨한 결합으로 시스템이 유연하고 객체 간의 의존성을 제거할 수 있다.
단점
1. 너무 많이 사용하게 되면, 상태 관리가 힘들 수 있습니다
퍼사드(Facade) 패턴 (0) | 2024.11.12 |
---|---|
팩토리 패턴 (팩토리 메서드 패턴, 추상 팩토리 패턴) (0) | 2021.12.09 |
디자인 패턴 정리 (2) | 2021.10.15 |
[싱글톤 패턴] Singleton Pattern (5) | 2021.10.13 |
프록시 패턴(Proxy Pattern) (1) | 2021.10.09 |
댓글 영역