ABOUT ME

-

Today
-
Yesterday
-
Total
-
  • 패턴 그리고 객체지향적 코딩의 법칙(문우식) 내용 정리 및 패턴 정리(2)
    컴퓨터 공부 ver 0.2/기타(책 등등) 2010. 9. 17. 13:31
    반응형

    1.      어댑터(Adapter) 패턴

    A.     다른 코드의 인터페이스와 내가 원하는 인터페이스가 서로 다를 때는 인터페이스 사이의 통신을 책임지는 클래스를 작성하는 것이 좋다.

    서로 다른 인터페이스에서 중재자 역할을 해주는 클래스를 보통 어댑터(Adapter)라고 부르며 디자인 패턴에서는 이를 어댑터 패턴이라고 부른다.

    B.     어댑터 패턴이 사용되는 경우

                    i.         보통 기존에 만들어져 있는 소스는 그 기능이 최적화되어 있다. 하지만 내가 만들려는 프로그램과 맞지 않을 수도 있다. 그럴 때 보통 사용하려는 소스를 고치는 경향이 있다고 한다. (아직 그래 본 적이 없어서 잘 모르겠다.) 그럴 경우 생각지 못한 버그를 만들어 낼 수 있다. 이때 사용되는 패턴이 어댑터 패턴이다.

                   ii.         안정성을 해치는 불필요한 코드 수정을 최소화하기 위한 목적으로 사용 가능.

                  iii.         변경사항이 발생했을 때 고쳐야 될 코드가 줄어들고 그만큼 테스트할 시간도 줄어든다. 이는 또 다른 말로 제품의 안정성을 확보할 시간이 많아진다는 뜻

    C.     또한 안정성이 확보된 소스를 수정할 경우 코드의 책임 소재가 불분명한 점도 간과할 수 없다.

    2.      옵저버(Observer) 패턴

    A.     정보 객체가 변경됐을 때 이 정보 객체를 참조하는 다른 객체들에게 변경사항을 알리어 변경된 정보를 즉각적으로 반영할 수 있는 방법

    B.     유의사항

                    i.         정보를 변경하는 쪽과 변경된 정보를 반영하는 쪽, 이 둘이 서로 공유하는 정보가 무엇이냐에 따라 코드가 달라진다.

    1.      복잡하고 큰 데이터를 가지는 경우, 구조체를 이용하던가 아니면 하나의 클래스로 묶는 방법으로 정보를 공유한다.

                   ii.         옵저버 패턴을 적용하기 위해서는 문제 상황을 정보의 변경과 변경된 정보의 반영으로 일반화시킬 수 있는 능력을 갖추어야 한다.

    C.     정보 객체를 소유하는 쪽을 서브젝트(Subject)라고 하며 정보 객체를 참조하는 객체를 옵저버(Observer)라고 한다.

                    i.         서브젝트와 옵저버의 관계 à 1 : n 관계

    3.      이터레이터(Iterator) 패턴

    A.     컬렉션(Collection)

                    i.         수집이라는 의미

                   ii.         프로그래밍에서는 비슷한 성질을 가지는 여러 객체들을 관리하기 쉽도록 모아 놓은 것

                  iii.         이터레이터(Iterator): 트래버스(Traverse)라고도 하며, 우리말로 탐색이라고도 한다.

    B.     이터레이터 패턴이 나온 배경

                    i.         컬렉션의 탐색을 위해 배열 같이 파라미터 전달을 위한 객체를 따로 만드는 것은 소모적인 방법

                   ii.         궁극적인 목적이 탐색이라면 탐색의 책임을 가지는 클래스(컬렉션이 직접 구현하거나 탐색 전용 클래스를 만들거나)를 따로 두어 탐색 외에 다른 액션을 취하지 못하도록 강제하여야 한다.

    C.     정의 및 의의

                    i.         컬렉션의 내부 구현과 탐색 방법을 분리시키는 방법

                   ii.         탐색하는 행위를 하나의 책임으로 보고 패턴화 했다는 점

    D.     가장 중요한 요소 커서

                    i.         커서가 컬렉션의 시작과 끝의 범위 안에서 정확히 동작해야 안전한 구현이 가능하다.

    E.      Passive 이터레이터 vs Active 이터레이터

                    i.         Passive 이터레이터

    1.      이터레이터용 클래스를 따로 구현하는 것을 Passive 이터레이터 혹은 외부 이터레이터라 한다.

    2.      별도의 클래스로 구현되어 있으므로 더 유연한 방법이 될 수 있다.

                   ii.         Active 이터레이터

    1.      내부 이터레이터라고도 한다.

    2.      private 변수들을 모두 접근할 수 있어서 더 강력한 기능을 제공

    3.      유연성 면에서는 조금 떨어지고 컬렉션 클래스에 책임이 많아 진다는 단점

    F.      만약 이터레이터를 사용 중에 배열 혹은 리스트에서 아이템이 제거되거나 추가되면?

                    i.         멀티 스레드일 경우 보통 다른 스레드에 의한 간섭이 일어나지 않도록 뮤텍스(Mutex)를 소유하고 탐색을 시작

    1.      하지만 뮤텍스를 소유하면 안전하기는 하지만 너무 오래 소유하고 있으면 다른 스레드들이 이 뮤텍스를 얻기 위해 기다리느라 전체적인 수행 속도는 늦어지게된다.

    2.      커서의 범위가 수시로 간섭 당할 수 있으므로 탐색 전에 범위의 간섭이 일어나지 않도록 해야 한다.

    4.      컴포지트(Composite) 패턴

    A.     연속적인 복합 구조에서 객체의 위치나 객체의 종류에 상관없이 모든 객체를 동일하게 다루고 연쇄반응을 가질 수 있도록 하는 방법

    B.     재귀적 합성을 사용

                    i.         재귀적 합성: 트리 구조에서 폴더 파일의 예처럼 폴더가 폴더를 가질 수 있는 것처럼 컨테이너(Container) 클래스가 다른 컨테이너(Container) 클래스를 가질 수 있는 방법

    1.      막연하게 트리 구조에 컴포지트 패턴을 사용하는 것은 효과적이지 못하다.

    C.     중첩된 소유 구조와 소유로 인해 생성된 트리 구조를 구성하고 탐색하기에 적합한 패턴. 객체지향의 큰 뼈대를 지탱하는 패턴이라 할 수 있다. 그러하기에 다른 패턴과 연관성이 많다.

    D.     중요 핵심: 개별 객체와 복합 객체를 코드상에서 따로 구분하지 않고 이들의 공통점으로 만들어진 인터페이스를 구성하는 것

    5.      스테이트(State) 패턴

    A.     클래스가 가지는 책임이 작다면 플래그를 사용하는 것이 효율적일 수 있다. 하지만 각 상태마다 동작하는 방식이 다르고 책임이 다르다면 상태만을 클래스화해서 상태 머신을 만들 수 있다.

    B.     스테이트 패턴을 구성하기 위한 개념

                    i.         상태를 의미하는 스테이트

                   ii.         이런 상태를 내부적으로 가지는(언어적으로는 멤버 변수를 가지고 있는) 컨텍스트(Context)이다. à 유저(클라이언트 코드)와 직접적으로 만나는 부분이고 유저는 이 컨텍스트와 통신한다.

    C.     복잡성을 낮추는 방법

                    i.         현재 상태는 오직 하나만 존재한다.

                   ii.         현재 상태에서 입력 조건에 따라 변화될 다음 상태만을 알면 된다.

    D.     스테이트 패턴을 적용하기 전에 가장 중요하게 생각하는 작업

                    i.         모든 상태 클래스의 행동을 분석해서 공통 인터페이스를 정의

                   ii.         정확한 상태의 변화. 상태의 변화를 분명하게 그릴 수 없다면 패턴은 곧 재앙을 부를 것이다. 두둥!!

    6.      스트래티지(Strategy) 패턴

    A.     우선 알아야 할 점!!

                    i.         효율성을 고려하지 않은 채 객체지향의 원칙에 충실한 것만으로는 좋은 코드라고 부르기에 미흡하다. 구조를 통해 효율성을 겸비한 유연한 코드를 얻을 수 있어야 한다.

                   ii.         상속 = 기능확장이라는 절대 항등식은 성립하지 않는다. 단순히 한 가지 기능만 사용하는데 상속은 너무 무거운 방법이다.

    B.     독립적으로 확장 가능한 다양한 알고리즘이 존재할 경우 각각의 방법을 클래스로 캡슐화하여 선택적 교체가 가능하도록 하는 방법

                    i.         동일한 인터페이스로 확장된 알고리즘은 클래스의 멤버 함수로 속해 있을 때보다 더 높은 확장성을 가진다.

    7.      프록시(Proxy) 패턴

    A.     클라이언트 코드에서 사용을 원하는 객체로의 접근을 제어하기 위한 목적으로 사용

    B.     내부적으로 자신이 제어하는 객체와 동일한 인터페이스를 클라이언트에게 제공하여 클라이언트가 통신을 원하는 객체와 직접적으로 통신하는 것처럼 믿게 만든다.

    C.     주의사항

                    i.         제어에 해당하는 책임을 통신을 원하는 객체나 클라이언트 코드가 가지지 않고 프록시가 가짐으로써 너무 무거운 책임을 가지는 객체를 만들어지지 않도록 한다.

                   ii.         원한다면 유동적으로 프록시 객체를 제거하여 제어에 해당하는 기능을 제거할 수 있는 유연함도 있다.

    8.      플라이웨이트(Flyweight) 패턴

    A.     대량으로 생성되는 객체들 사이의 중복되는 정보를 공유, 메모리적인 효율성을 높이는 방법이다.

    B.     중복된 정보를 공유하는 방법은 싱글턴, 팩토리, 자원 풀(Resource Pool)등이 열러 방법으로 구현될 수 있다.

     

    9.      커맨드(Command) 패턴

    A.     객체의 행동을 별도의 클래스에 캡슐화해서 행동 객체에 확장성을 부여한다. 각각의 커맨드들은 특정 객체에 의존하지 않도록 만들어지므로 재활용성이 매우 높다.

    B.     JAVA UI 이벤트 처리 모델과 같이 행동의 책임을 분산시키기에 좋은 방법

                    i.         커맨드의 책임을 다하도록 필요한 객체들에 접근할 수 있는 방법이 마련되어야 함

    10.    데코레이터(Decorator) 패턴

    A.     기본 기능을 하는 객체와 이 객체를 기반으로 동작하는 데코레이터들을 조합하여 기능을 확장하는 방법

                    i.         상속보다는 유연한 방법으로 동적으로 기능을 추가/삭제 할 수 있고 조합해서 쓸 수 있다는 장접

                   ii.         JAVA I/O모델이 대표적인 사례



    마지막에는 집중도가 떨어져서 그냥 책에 내와있는 요점 정리만 정리했네요. 책 사서 보세요. 책은 좋은 겁니다!!!


    반응형

    댓글

Designed by Tistory.