디자인 패턴
이란 프로그램을 설계할 때 발생했던 문제점들을 객체 간의 상호 관계 등을 이용하여 해결할 수 있도록 하나의 '규약' 형태로 만들어 놓은 것을 의미한다.
process가 실행중에 오직 하나의 object만 생성되도록 강제하는 디자인 패턴 / 하나의 class에 오직 하나의 인스턴스만 가지는 패턴
ex) 어플 사용 시 세팅에서 다크 모드로 설정해두면 다른 페이지로 이동하더라도 이 다크모드가 그대로 유지되어야 한다. → 어떤 페이지에 있던 이 세팅을 관리하는 객체는 반드시 같은 것을 사용해야 한다.
일반적으로 하나의 class로 개별적인 object를 생성해 두개의 서로 다른 object를 만들면, process 안에서는 각각의 메모리 공간을 가진다. ➡️ 동적 공간
반면, singleton 디자인 패턴을 가진 class를 사용해서 여러개의 object를 만들경우 모두 단 하나의 object만 가리킨다. 결과적으로 process 전체에서 object는 지정된 하나의 메모리 공간만 차지하게 된다. ➡️ 정적 공간
나중에 아무리 많은 object를 만들더라도 이를 나타내는 이름만 다를 뿐이지 결국 같은 object를 가리킨다.
하나의 object가 리소스를 많이 차지할 경우, 또는 해당 object가 외부 네트워크와 연결이 되는데 이 연결 네트워크가 단 한개만 있어야 할 경우 singleton pattern이 필요하다.(보통 데이터베이스 연결 모듈에 많이 사용)
장점 : 인스턴스 생성 비용 감소
단점 : 의존성 높아짐 ➡️ '의존성 주입'을 통해 해결 가능
상속 관계의 두 class에서 상위 클래스가 뼈대를 형성하고, 하위 클래스에서 객체 생성에 관한 구체적인 내용 결정
클라이언트가 object의 생성 방법을 몰라도 factory에 어떤 object를 만들지 요청만 하면 쉽게 받을 수 있다.
즉, 복잡한 object의 생성 과정을 클라이언트가 직접 다룰 필요 없이 factory안에 숨겨놓고, 클라이언트는 간단하게 필요한 것을 요구하면 factory가 필요한 object를 만들어 return 해준다.
느슨한 결합을 가지며, 유연성이 커 유지 보수에 용이하다.
Factory를 더 확장시켰다.
Factory에 여러 기능을 추가하고 싶을 경우
하나의 factory에서 여러 객체를 만드는 것이 아니라 각각의 다른 기능이 있는 factory에서 각각의 객체를 만든다.
Factory method가 들어있는 factory interface를 만들고, 각 factory들이 이를 상속받음으로써 각각의 factory들에도 이 method가 있다.
객체의 행위를 바꾸고 싶은 경우 직접 수정하지 않고, 캡슐화한 알고리즘을 컨텍스트 안에서 바꿔주면서 상호 교체가 가능하게 만드는 패턴
ex) 프로그램 실행 중 모드가 바뀔 때마다 검색이 이루어지는 방식, 즉 '전략'이 수정되는 것
옵션들마다 행동들을 모듈화해서 독립적이고 상호 교체 가능하게 만드는 것
지정된 특정 메서드가 모듈화된 모드에 따라 다르게 실행되도록 하는 것
Subscriber / Listener
주체(객체의 상태 변화를 보는 관찰자)가 객체의 상태가 변했을 때마다 옵저버(추가 변화 사항이 생기는 객체)들에게 변화를 알려주는 디자인 패턴
이벤트가 일어나는 순간, 이를 바라보는 옵저버들이 반응하게 만드는 것이 가능하다.
옵저버 패턴을 가지지 않는다면, 이벤트를 체크해야하는 객체들은 매 1초, 1분, 1시간 마다 계속해서 이를 확인해야 한다(polling). → 필요없는 리소스의 낭비가 생김. 또는 1시간 내에 이벤트가 생겼다 사라지면 이벤트가 일어났었는지 알 수도 없다.
옵저버들의 등록, notify() 함수를 통한 옵저버들의 함수 호출을 기억한다면 필요에 따라 옵저버 패턴 응용이 가능하다.
대상 객체에 접근하기 전 그 접근에 대한 흐름을 가로채 대상 객체 앞단의 인터페이스 역할을 하는 디자인 패턴
프로그래밍에서 사용되는 클래스들 중에서도 인터넷에서 받아와야해서 시간이 걸리거나 메모리를 많이 차지하거나 하는 등의 이유로 객체로 여럿 생성하기가 부담스러운 것들이 있다. → 대리인 역할을 하는 클래스를 따로 두어, 가벼운 일을 처리하게 한다.
ex) 유튜브 썸네일에서 기본적으로는 제목이 나타나고 마우스를 해당 영상에 가져가면 프리뷰 영상이 실행된다. 제목을 화면에 나타내는 가벼운 작업은 프록시로 생성되게 하고, 프리뷰 영상을 보여주는 무거운 작업은 실제 클래스가 담당하게 한다.
프록시 서버 : 클라이언트가 자신을 통해 다른 네트워크 서비스에 간접적으로 접속할 수 있게 해주는 컴퓨터 시스템이나 응용 프로그램
이터레이터를 사용하여 컬렉션의 요소들에 접근하는 디자인 패턴으로, 순회할 수 있는 여러 가지 자료형의 구조와는 상관없이 이터레이터라는 하나의 인터페이스로 순회 가능하다.
collection 요소를 순서, 정렬, 중복 여부 등 구현 방식에는 관계없이 조회에만 집중하는 인터페이스
모델(Model), 뷰(View), 컨트롤러(Controller)로 이루어진 디자인 패턴
재사용성, 확장성 용이 but 애플리케이션이 복잡해질수록 모델과 뷰의 관계가 복잡해짐
MVC 패턴에서 파생됨. 컨트롤러가 프레젠터(Presenter)로 교체된 패턴
뷰와 프레젠터는 일대일 관계이므로 MVC보다 더 강한 결합을 지닌다.
MVC 패턴에서 파생됨. 컨트롤러가 뷰모델(View Model)로 바뀐 패턴
MVC 패턴과는 다르게 커맨드와 데이터 바인딩을 가짐. 뷰와 뷰모델 사이의 양방향 데이터 바인딩 지원
UI를 별도의 코드 수정 없이 재사용 가능
단위 테스팅에 용이
특정 상태마다 다르게 할 일을, 나아가서 상태 자체를 그 상태마다 실행시 할 일과 함께 하나하나 모듈화해서 지정해둠 (vs. strategy: 어떤 동일한 틀 안에 있는 특정 작업의 방식, 모드를 바꿔줄 때)
ex) TV가 꺼진 상태에서 누르면 켜지고, 켜진 상태에서 누르면 꺼지는 버튼 / 다크모드 여부를 껐다 켰다 하는 스위치
지정된 특정 메서드가 실행될 때 모드도 전환되도록 하는 것
strategy pattern이 같은 일을 하되, 그 알고리즘이나 방식이 갈아끼워지는 것이라면 command pattern은 하는 일 자체가 다르다.
모드 변경에 따라 명령을 갈아끼워넣는 식으로 작성되기도 하고, 스위치를 올릴 때와 내릴 때에 각각 다른 명령을 심어주는 식으로 짜기도 하고, 여러 명령들을 목록으로 실어보내서 차례로 실행시킬 수도 있다.
커맨드 패턴을 잘 응용하면 각종 생산성 툴처럼 여러 작업을 수행한 뒤 뒤로가기나 앞으로가기를 구현하는 등 다양한 방식으로 활용될 수 있다.
<참고>
https://www.youtube.com/@user-pw9fm4gc7e
https://www.youtube.com/@yalco-coding