싱글톤패턴
의도: 한클래스가 오직 하나의 인스턴스만을 갖도록 하고, 이 인스턴스에 접근할수있는 광범위한 지시자(글로벌 포인터) 를 제공한다.
싱글톤패턴은 어떻게 작동하는가?
원하는 객체를 인스턴스 화하기 위해 이용되는 특별한 메소드를 가짐으로써 작동한다.
-> 이 메소드가 호출될때 , 객체가 이미 인스턴스화 되었는지를 체크한다.
이미 인스턴스가 존재한다면 이에 대한 레퍼런스를 반환한다.만약 그렇지 않다면 , 이객체를 새로 인스턴스화 하고 이 인스턴스에 대한 레퍼런스를 반환한다
-> 이 타입의 객체가 인스턴스화 되는 방법은 오직 한 가지라는것을 보장하기 위해, 그 클래스의 생성자를 protected 또는 private 으로 정의한다.
싱글톤 패턴: 핵심 특징
의도: 오직 하나의 객체만을 갖고 싶지만 이 객체의 인스턴스화를 제어하는 전역 객체는 없어야한다.
문제점: 몇몇 다른 클라이언트 객체가 동일한 객체를 참조 해야 하고 본인은 클라이언트가 참조하는 객체가 단 하나만 존재하는것을 보증하고 싶다.
해결법: 하나의 인스턴스만이 존재한다는것을 보장하자,
참여자와 협력자: 클라이언트는 오직 getinstance 메소드를 통해서만 Singleton 으 인스턴스를 생성한다
결과: 클라이언트는 singleton 의 인스턴스가 존재하는지를 신경쓸 필요가 없다.
이는 singleton 안에서 제어된다.
구현 : 클라이언트가 원하는 객체를 참조하는 클래스의 private static 멤버 변수를 추가하자(초기값은 NULL 이다.)
만약 이 멤버 변수가 NULL 이면 이 클래스를 인스턴스화하는 public static 메소드를 추가하고(그리고 인스턴스화를 수행해 이 멤버 변수의 값을 설정하고),
그 후에 이 멤버 변수의 값을 반환하자.
어떠한 객체도 이 클래스를 직접적으로 인스턴스화 할수 없고 static 생성자 메커니즘을 통해서만 인스턴스화 할수 있도록 생성자의 접근 가능성을
protected 또는 private 으로 설정하자.
상태 패턴
객체의 내부 상태 정보를 별도의 클래스 상속 구조로 정의 해서 사용하는것을 상태 패턴이라고 한다.
상태패턴의 가장 큰 장점은 새로운 상태의 추가 및 추가된 상태를 포함해서 상태 변화에 따른 행위수행 변경이 손쉽게 이루어 질수 있다는것이다.
상태패턴이 이 같은 장점을 가지는 이유는 크게 클래스 상속과 다형성에 기인한다.
즉 새로운 상태 추가가 쉬운 것은 상태정보가 클래스 상속 구조 형태로 정의 되므로, 하위 클래스를 추가하기만 하면 새로운 상태 추가가 가능하기
때문이며, 새로 상태가 추가되더라도 상태 변화에 따른 행위 수행 변경이 쉬운것은 새로 추가되는 하위 상태 클래스가 최상위의 상태클래스가 가지고 있는
인터페이스를 자신의 상태에 맞추어 오버라이딩하여 구현하기만 하면, 이를 이용하는 객체 입장에서는 별다른 수정없이 다형성에 의해
원하는 작업을 수행할수있기 때문이다.
상태패턴의 장단점:
상태패턴은 수행할 행위를 결정하기 위해 객체 내부에서 상태값을 비교하는 문장을 없앨수있게 해준다.
이러한 문장이 없어짐으로써 해당 객체는 자기 내부에 포함하고 있는 상태 정보와는 독립적인 동작이 가능하며,하나의 모듈이 너무 길어지거나
너무 많은 조건 비교를 포함하지 않게 만들어준다.
상태패턴은 특정 상태와 관련된 행위들을 하나의 객체로 모아주는 역활을 한다.이를 통해 상태패턴은 동일한 상태에서 이루어지는 행위들을 국지화시켜 유지
보수 할수있게 해준다.
상태패턴을 적용할경우에는 객체의 상태 전환이 명백히 드러난다.왜냐면 상태패턴의 경우 상태 전환이 일어나면 참조하는 객체가 바뀌기 때문이다.
반면 상태패턴을 적용하지않을경우 객체의 상태 변화가 내부 데이터 멤버 값의 변화로 표현되기 때문에 잘 드러나지않는 단점이 있다.
상태패턴은 상태 정보가 일관성을 가지게 만들어준다.
상태패턴을 사용하지 않을경우 : 만일 데이터 멤버로 객체의 상태를 관리할 경우 데이터 멤버 값 여러개 바꾸는 과정에서 일관성이 깨지는 현상이 발생할수있다.
주의 할점: 상태패턴을 사용하면 새로운 상태의 추가나 추가된 상태를 포함해서 상태 변화에 따른 행위 수행 변경을 반영하기 쉽다.
무턱대로 상태패턴을 적용하는것은 불필요하게 클래스가 많아지는 문제를 야기함
따라서 상태패턴은 객체 내부에서 저장,관리하고있는 상태의 종류가 더 추가될 가능성이 있는지,또 특정 상태에서 수행해야할 행위들을 하나로 모을 필요가
있는지 등을 종합적으로 고려해서 적용여부를 판단해야함
command patrern
요청을 처리할 작업을 일반화시켜 요청의 종류와는 무관하게 프로그램 작서이 가능하게 만들어주는것
유용하게 사용:
그래픽 사용자 인터페이스 등을 구현시 메뉴나 버튼에 수행할 작업을 일반화 시켜 설정하고자 할때 유용함
특히 경우에따라서는 동일한 메뉴에 대해서 동적으로 다른 command 클래스 객체를 설정함으로써 동일한 메뉴나 버튼이 선택되더라도 상황에 따라
다른 작업을 수행하게 만들수도있다.
작업 수행을 요청한 시점과 실제 작업을 수행하는 시점을 달리 하고 싶을때도 유용함
왜냐? 직접 수행할 작업에 대한 함수를 불러주는 형태가 아니라 수행할 작업에 대한 객체를 먼저 생성하고 , 나중에 작업 수행을 요청하는 형태이므로,
수행할 작업을 큐 등에 쌓아 두었다가 작업 수행이 필요한 시점에 작업을 수행하는것이 가능하기 때문이다.
장점:
작업 수행을 요청하는 객체와 실제 작업을 수행하는 객체를 분리시켜주므로 시스템의 결합도가 낮아질수있으며, 두 객체가 독립적으로 변경가능한장점
을 가진다.
command 및 그 하위 클래스는 기존 클래스와 무관하게 확장이 가능하며, 확장된 클래스들은 client 의 별다른 수정없이 사용이 가능하다.
이런 이유로 command 패턴을 적용할 경우 새로운 종류의 작업처리를 추가하기가 매우 쉽다.
--> command 패턴은 외부로부터 요청이 전달될때 이를 받아주는 프로그램 모듈은 미리 작성해두고,각각의 요청에 대해 요청처리를 수행하는
모듈은 개별 응용프로그램마다 플러그인 시키는 콜백 형태의 프로그램 작성에 매우 유용함
팩토리 패턴
서로다른 두개의 패턴, 즉 팩토리 메서드 패턴과 추상 팩토리 패턴을 의미한다.
팩토리 메서드 패턴은 객체를 생성하는 인터페이스(팩토리객체)를 정의하고 어떤 객체인스턴스를 만들지는 팩토리 객체를
상속받아 구현하는 서브 클래스에서 결정하여 객체를 만들도록 하는 패턴을 의미한다
즉 팩토리 메서드 패턴은 클래스 인스턴스를 만들어주는 클래스(팩토리)를 두는것이라고보면 된다(
(객체를 생성하는 인터페이스(팩토리 객체)를 정의하고)
만일 해당 팩토리 클래스에서 직접 클래스 인스턴스를 만든다면 이는 simple factory pattern 이된다.
이경우 구현이 간단하지만 구현 클래스에 의해 유연성이 감소하게 되는 단점이 된다.여기에 실제 인스턴스를 만드는 역활을
서브 클래스에 두는것이 팩토리 메서드 패턴이라 할수있다.
(어떤 객체 인스턴스를 만들지는 팩토리 객체를 상속받아 구현하는 서브 클래스에서 결정한다)
추상 팩토리 패턴은 서로 연관된 또는 의존적인 '객체의집합'을 만들때 사용되는 인터페이스(팩토리객체)를 만들고 그 인터페이스를
상속받아 구현 하는 서브 클래스에 의해 실제 객체의 집합을 만들도록 하는 패턴을 의미한다.
추상팩토리 패턴은 객체의 집합을 만들때 유용하다.
특정 객체를 만들때는 팩토리 메소드 패턴을 사용
그렇게 만들어진 객체를 구성하는 멤버 객체들을 만드는데는 추상 팩토리 패턴을 사용한다.
Adapter 패턴
한클래스의 인터페이스를 클라이언트들이 기대하는 또 다른 인터페이스로 전환한다.
adapter 패턴은 클래스들이 상호호환이 되지않는 인터페이스 때문에 다른 클래스들과 함께 작동하지못하는것을 함께 작동하게 해준다.
기본적으로 "올바른 작업을 수행하지만 잘못된 인터페이스를 가진 객체를 위해 새로운 인터페이스를 생성해내기 위한 방법이 필요하다"라는것을 말한다.
클래스 (또는 클래스들)의 인터페이스를 또 다른 인터페이스로 전화하는데 매우 유용한 패턴이다.
이 패턴은 원하는 인터페이스를 가진 새로운 클래스를 생성하고,그런다음 적응시키는 객체를 효과적으로 포함하기 위해
본래의 클래스메소드로 감싸는것으로구현가능하다.