본문 바로가기

디자인 패턴

디자인 패턴 - 옵저버 패턴(Observer Pattern)

1. 정의

  • 주제(subject)의 상태가 바뀌면 그 객체에 의존하는 다른 객체(observer)에게 연락이 가고 자동으로 내용이 갱신되는 방식으로 일대다(one-to-many) 의존성을 정의한다.

2. 예시

  • 엄마, 아빠에게 자식의 성적을 알린다.

3. 그림

4. 클래스 다이어그램

5. 코드

public class Client {
    public static void main(String[] args){
        Child child = new Child();

        Mother mom = new Mother(child); // 엄마만 등록
        child.setValue(100);

        child.removeObserver(mom); // 엄마 삭제
        System.out.println("---------");

        Father dad = new Father(child); // 아빠만 등록
        child.setValue(70);

        child.removeObserver(dad); // 아빠 삭제
        System.out.println("---------");

        // 엄마, 아빠 등록
        mom = new Mother(child);
        dad = new Father(child);
        child.setValue(70);
    }
}
/* 출력
엄마 : 100
---------
아빠 : 70
---------
엄마 : 70
아빠 : 70

*/
public interface Observer {
    void update(int value);
}
public interface Subject {
    void registerObserver(Observer o);
    void removeObserver(Observer o);
    void notifyObservers();
}
public interface Display {
    void display();
}
import java.util.ArrayList;
import java.util.List;

public class Child implements Subject{
    private List<Observer> observers;
    private int value;

    public Child() {
        this.observers = new ArrayList<>();
    }

    @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(value);
        }
    }

    public void setValue(int value){
        this.value = value;
        notifyObservers();
    }
}
public class Mother implements Observer, Display{
    private Subject subject;
    private int value;

    public Mother(Subject subject) {
        this.subject = subject;
        subject.registerObserver(this);
    }

    @Override
    public void update(int value) {
        this.value = value;
        display();
    }

    @Override
    public void display() {
        System.out.println("엄마 : "+this.value);
    }
}
public class Father implements Observer, Display{
    private Subject subject;
    private int value;

    public Father(Subject subject) {
        this.subject = subject;
        subject.registerObserver(this);
    }

    @Override
    public void update(int value) {
        this.value = value;
        display();
    }

    @Override
    public void display() {
        System.out.println("아빠 : "+this.value);
    }
}

https://github.com/kang-seongbeom/design_pattern

💡 Github에서 디자인 패턴 코드를 볼 수 있습니다.

 

6. 설명

  • Subject를 구현하는 Child에 등록하고 싶은 Observer 구현체(엄마, 아빠)를 등록한다.
  • child.setValue()를 하면 값을 저장(상태 변경)하고, 반복문을 통해 notifyObservers()를 하여 등록된 옵저버에게 연락한다.
  • removeObserver()를 통해 등록된 옵저버를 삭제할 수 있다.