CS

디자인 패턴2

blackmilktea 2024. 1. 13. 23:48

4. 옵저버 패턴(Observer pattern)

주체가 어떤 객체(subject)의 상태 변화를 관찰하다가 상태 변화가 있을 때마다

메서드 등을 통해 옵저버 목록에 있는 옵저버들에게 변화를 알려주는 디자인 패턴

옵저버 패턴은 주로 이벤트 기반 시스템에 사용함.

여기서 주체란 객체의 상태 변화를 보고 있는 관찰자
옵저버는 객체의 상태 변화에 따라 전달되는 메서드 등을 기반으로 '추가 변화 사항'이 생기는 객체

 

트위터는 옵저버 패턴을 활용한 서비스

MVC(Model-View-Controller) 패턴에도 사용

주체(Model)에서 변경 사항이 생겨 update() 메서드로 옵저버(View)에 알려주고 이를 기반으로 Controller 등이 작동

 

topic이라는 주체이자 객체를 기반으로 옵저버 패턴을 구현한 java_code

더보기
import java.util.ArrayList;
import java.util.List;

interface Subject {
    public void register(Observer obj);
    public void unregister(Observer obj);
    public void notifyObservers();
    public Object getUpdate(Observer obj);
}

interface Observer {
    public void update(); 
}

class Topic implements Subject {
    private List<Observer> observers;
    private String message; 

    public Topic() {
        this.observers = new ArrayList<>();
        this.message = "";
    }

    @Override
    public void register(Observer obj) {
        if (!observers.contains(obj)) observers.add(obj); 
    }

    @Override
    public void unregister(Observer obj) {
        observers.remove(obj); 
    }

    @Override
    public void notifyObservers() {   
        this.observers.forEach(Observer::update); 
    }

    @Override
    public Object getUpdate(Observer obj) {
        return this.message;
    } 
    
    public void postMessage(String msg) {
        System.out.println("Message sended to Topic: " + msg);
        this.message = msg; 
        notifyObservers();
    }
}

class TopicSubscriber implements Observer {
    private String name;
    private Subject topic;

    public TopicSubscriber(String name, Subject topic) {
        this.name = name;
        this.topic = topic;
    }

    @Override
    public void update() {
        String msg = (String) topic.getUpdate(this); 
        System.out.println(name + ":: got message >> " + msg); 
    } 
}

public class HelloWorld { 
    public static void main(String[] args) {
        Topic topic = new Topic(); 
        Observer a = new TopicSubscriber("a", topic);
        Observer b = new TopicSubscriber("b", topic);
        Observer c = new TopicSubscriber("c", topic);
        topic.register(a);
        topic.register(b);
        topic.register(c); 
   
        topic.postMessage("amumu is op champion!!"); 
    }
}
/*
Message sended to Topic: amumu is op champion!!
a:: got message >> amumu is op champion!!
b:: got message >> amumu is op champion!!
c:: got message >> amumu is op champion!!
*/

 

 

5. 프록시 패턴(Proxy pattern)

프록시 패턴은 대상 객체(subject)에 접근하기 전 그 접근에 대한 흐름을 가로채 해당 접근을 필터링하거나 수정하는 등의 역할을 하는 계층이 있는 디자인 패턴

이를 통해 객체의 속성, 변환 등을 보완하며 보안, 데이터 검증, 캐싱, 로깅에 사용

 

6. 이터레이터 패턴(Iterator pattern)

이터레이터(Iterator)를 사용하여 컬랙션(Collection)의 요소들에 접근하는 디자인 패턴

여러 가지 자료형의 구조와는 상관없이 이터레이터라는 하나의 인터페이스로 순회가 가능

 

7. 노출모듈 패턴(Revealing module pattern)

즉시 실행 함수를 통해 private, public 같은 접근 제어자를 만드는 패턴

 

자바스크립트는 private나 public 같은 접근 제어자가 존재하지 않고 전역 범위에서 스크립트가 실행되기 때문에 노출모듈 패턴을 통해 접근 제어자를 구현하기도 함.

js_code

더보기
const pukuba = (() => {
    const a = 1
    const b = () => 2
    const public = {
        c : 2, 
        d : () => 3
    }
    return public 
})() 
console.log(pukuba)
console.log(pukuba.a)
// { c: 2, d: [Function: d] }
// undefined
// a, b는 다른 모듈에서 사용할 수 없는 private 범위를 가짐.

 

8. MVC 패턴

Model, View, Controller로 이루어진 디자인 패턴

애플리케이션의 구성 요소를 세 가지 역할로 구분하여 개발 프로세스에서 각각의 구성 요소에만 집중해서 개발 가능

장점: 재사용성과 확장성이 용이
단점: 애플리케이션이 복잡해질수록 모델과 뷰의 관계가 복잡해짐

모델   컨트롤러  
애플리케이션의 데이터인 데이터베이스, 상수, 변수 등

뷰에서 데이터를 생성하거나 수정하면 컨트롤러를 통해 모델을 생성하거나 갱신
갱신
<----
---->
유저 이벤트
모델과 뷰를 잇는 다리 역할, 이벤트 등 메인 로직을 담당
모델과 뷰의 생명주기 관리

모델이나 뷰의 변경 통지를 받으면 이를 해석하여 각각의 구성 요소에 해당 내용에 대해 알려줌
갱신
---->
<----
알림
모델을 기반으로 사용자가 볼 수 있는 화면, 모델이 가지고 있는 정보를 따로 저장하지 않아야 하며 화면에 표시하는 정보만 가지고 있어야 함.
변경이 일어나면 컨트롤러에 알려야 함.

 

자바 플랫폼을 위한 오픈 소스 애플리케이션 프레임워크인 스프링(Spring)은 MVC 패턴을 이용한 대표적인 프레임워크

 

9. MVP 패턴

MVC에서 Controller가 Presenter로 교체된 패턴

컨트롤러는 하나 이상의 뷰와 연결될 수 있지만

프레젠터는 일대일 관계이기 때문에 MVC 패턴보다 더 강한 결합을 지님.

 

10. MVVM 패턴

MVC에서 Controler가 View Model로 바뀐 패턴

뷰 모델은 뷰를 더 추상화한 계층, 커맨드(Command)데이터 바인딩(Data binding)을 가지는 것이 특징

뷰와 뷰모델 사이의 양방향 데이터 바인딩을 지원하며

UI를 별도의 코드 수정 없이 재사용할 수 있고 단위 데스팅 하기 쉬움.

커맨드(Command): 여러 가지 요소에 대한 처리를 하나의 액션으로 처리할 수 있게 하는 기법
데이터 바인딩(Data binding): 화면에 보이는 데이터와 웹 브라우저의 메모리 데이터를 일치시키는 기법
뷰 모델을 변경하면 뷰가 변경됨.

 

반응형이 특징인 프런트엔트 프레임 워크 Vue.js가 MVVM 패턴을 가진 대표적인 프레임워크

함수를 사용하지 않고 값 대입만으로도 변수가 변경, 양방향 바인딩, html을 토대로 컴포넌트 구축 가능

재사용 가능한 컴포넌트 기반으로 UI를 구축할 수 있으며 BMW, 구글, 루이비통 등에서 사용

 

 

'면접을 위한 CS 전공지식 노트'를 기반으로 작성한 글입니다.

저자 블로그 https://blog.naver.com/jhc9639/222704234059