'프로그래밍 > 디자인패턴' 카테고리의 다른 글

디자인패턴요약  (0) 2018.06.11
디자인 패턴 요약  (0) 2018.06.11
쉽게 배우는 Template 패턴  (0) 2017.01.29
쉽게 배우는 Builder 패턴  (0) 2017.01.29
쉽게 배우는 Adapter 패턴 (아답터 패턴)  (0) 2017.01.29
블로그 이미지

낭만가을

,

GoF(Gang of Four)에서는 23가지 디자인 패턴을 3가지 유형으로 분류합니다.

A. Creational Pattern

  • 객체를 생성하는데 관련된 패턴들
  • 객체가 생성되는 과정의 유연성을 높이고 코드의 유지를 쉽게 함

B. Structural Pattern

  • 프로그램 구조에 관련된 패턴들
  • 프로그램 내의 자료구조나 인터페이스 구조 등 프로그램의 구조를 설계하는데 활용할 수 있는 패턴들

C. Behavioral Pattern

  • 반복적으로 사용되는 객체들의 상호작용을 패턴화 해놓은 것들


주요 디자인 패턴만 정리했습니다.

1. 어댑터 패턴(Adapter Pattern)

  • 용도
    • 어떤 클래스를 우리가 바로 사용할 수 없을 때가 있다. 다른 곳에서 개발한 클래스고, 우리가 그것을 수정할 수 없을 때, 우리에게 맞게 중간에 변환할 역할을 해줄 수 있는 클래스가 필요한데, 그것이 바로 어댑터이다.
  • 사용 방법
    • 상속
    • 위임: 어떤 메소드의 실제 처리를 다른 인스턴스의 메소드에게 맡기는 방법
  • Class Diagram

2. 프로토 타입 패턴(Prototype Pattern)

  • 용도
    • 미리 만들어진 객체를 복사해서 객체를 생성하는 방식
    • 객체를 많이 만들어야 할 경우, 객체 생성에 드는 코딩 분량을 현저히 줄일 수 있다
    • 클래스로부터 객체를 생성하기 어려운 경우(그래픽 에디터에서 사용자의 마우스 클릭으로 생성되는 객체들)
  • 사용 방법
    • 모형(Prototype) 인스턴스를 등록해 놓고, 등록된 인스턴스를 복사(clone())해서 인스턴스를 생성함
  • Class Diagram

3. 싱글톤 패턴(Singleton Pattern)

  • 용도
    • 시스템 내부에 1개의 인스턴스만 생성하고 싶은 경우
      • 컴퓨터 자체를 표현한 클래스
      • 현재 시스템 설정을 표현한 클래스
  • 사용 방법
    • 생성자를 private으로 선언하고, 해당하는 생성자를 클래스 내부에서만 호출함
  • Class Diagram

4. 컴포지트 패턴(Composite Pattern)

  • 용도
    • 틀과 내용물을 같은 것으로 취급하고 싶을 때(디렉토리 내부에는 디렉토리와 파일이 있지만, 둘 모두 디렉토리 내부에 있는 Element로 표현하고 싶을 때)
  • 사용 방법
    • Composite클래스가 Component를 포함하도록 함
  • Class Diagram// Composite이 Component를 포함하고 있음

5. 데코레이터 패턴(Decorator Pattern)

  • 용도
    • 데코레이팅한 결과물을 다시 내용물로 보고 그것을 다시 데코레이팅하기 위함(지속적으로 장식을 추가할 때, 문자열 주위에 여러 유형의 border 장식을 추가할 때)
  • 사용 방법
    • Border 클래스가 다시 Display를 포함함(컴포지트랑 비슷)
  • Class Diagram// Decorator가 Component를 포함하고 있음

6. 퍼사드 패턴(Facade Pattern)

  • 용도
    • 대규모 프로그램에는 서로 관련있는 클래스들이 많음 -> 복잡하게 얽혀있는 클래스들을 정리해서 높은 레벨의 인터페이스(API)를 제공(간단하게 접근가능)
    • 여러 클래스들을 직접 제어하지 않고 ‘창구(facade)’에 요구함
    • 결과적으로 구현시에 간단한 인터페이스를 사용할 수 있게
  • 사용 방법
    • 여러 클래스들의 기능들을 묶은 Facade 클래스를 만들고 Facade 클래스에 접근함
  • Class Diagram

7. 프록시 패턴(Proxy Pattern)

  • 용도
    • Proxy는 대리인이라는 의미, 시간이 많이 걸리는 작업을 할 때 사용함
    • 시간이 많이 걸리는 작업을 할 때, 대리인이 할 수 있는 일은 대리인이 하고 할 수 없는 일(Heavy job)은 본래의 클래스에게 넘겨줌
      • 시스템 초기화는 필요하지 않은 기능까지 초기화하려고 하면 많은 시간이 필요한데, 그 기능을 Proxy에 위임함
      • 프린트 프로그램에서 실제 프린터를 실행하는 과정에 시간이 오래 걸리기 때문에 그 과정에 있는 일들을 Proxy에 위임함
  • 사용 방법
    • Proxy클래스에 우선 일을 위임하고, 그 뒤에 RealSubject가 해야할 일은 넘겨주는 방법으로 사용
  • Class Diagram

8. 옵저버 패턴(Observer Pattern)

  • 용도
    • 관찰 대상의 상태가 변화했을 때 관찰자에게 통지하는 패턴
    • 상태 변화에 따른 처리를 기술할 때 효과적으로 활용(MVC패턴에서 Model과 View의 분리 등)
  • 사용 방법
    • Observer 클래스에 상태 변화를 알려주고, Observer는 다시 그 변화에 맞는 결과를 나타냄
  • Class Diagram

  • 구현 및 Code

  • Observer Class
public interface Observer {
public abstract void update(NumberGenerator generator);
}
  • NumberGenerator
import java.util.Vector;
import java.util.Iterator;
public abstract class NumberGenerator {
private Vector observers = new Vector(); // Observer들을 보관
public void addObserver(Observer observer) { // Observer를 추가
observers.add(observer);
}
public void deleteObserver(Observer observer) { // Observer를 삭제
observers.remove(observer);
}
public void notifyObservers() { // Observer에 통지
Iterator it = observers.iterator();
while (it.hasNext()) {
Observer o = (Observer) it.next();
o.update(this);
}
}
public abstract int getNumber(); // 수를 취득한다.
public abstract void execute(); // 수를 생성한다.
}
  • RandomNumberGenerator
import java.util.Random;
public class RandomNumberGenerator extends NumberGenerator {
private Random random = new Random(); // 난수발생기
private int number; // 현재의 수
public int getNumber() { // 수를 취득한다.
return number;
}
public void execute() {
for (int i = 0; i < 20; i++) {
number = random.nextInt(50);
notifyObservers();
}
}
}
  • DigitObserver
public class DigitObserver implements Observer {
public void update(NumberGenerator generator) {
System.out.println("DigitObserver:" + generator.getNumber());
try {
Thread.sleep(100);
} catch (InterruptedException e) {
}
}
}
  • GraphObserver
public class GraphObserver implements Observer {
public void update(NumberGenerator generator) {
System.out.print("GraphObserver:");
int count = generator.getNumber();
for (int i = 0; i < count; i++) {
System.out.print("*");
}
System.out.println("");
try {
Thread.sleep(100);
} catch (InterruptedException e) {
}
}
}
  • Main
public class Main {
public static void main(String[] args) {
NumberGenerator generator = new RandomNumberGenerator();
Observer observer1 = new DigitObserver();
Observer observer2 = new GraphObserver();
generator.addObserver(observer1);
generator.addObserver(observer2);
generator.execute();
}
}

9. 커맨드 패턴(Proxy Pattern)

  • 용도
    • 실행하고 싶은 메소드의 History 관리(우리가 Ctrl + z를 눌러서 실행취소를 한다고 할 때, History를 저장할 수 있어야 가능함)
    • 매크로 명령을 정의하고자 할 때
    • 동일한 명령을 반복해서 실행할 때
  • 사용 방법
    • 명령어를 객체에 캡슐화해 저장함(주로 스택으로 저장)
  • Class Diagram

10. 책임 연쇄 패턴(Chain of Responsibility Pattern)

  • 용도
    • 어떤 요구가 발생했을 때, 그 요구를 처리할 Object를 바로 결정할 수 없을 때, 다수의 Object를 Chain으로 연결해 차례로 방문하면서 목적에 맞는 Object를 결정함(내가 못하면 남한테 전가시킴)
    • 요구하는 측과 처리하는 측의 연결을 약화시킴(Coupling을 낮추는 역할을 함)
  • 사용 방법
    • Handler객체가 문제를 해결했는지 확인하면서 계속해서 가능한 객체를 연결해 줌
  • Class Diagram

11. 중재자 패턴(Mediator Pattern)

  • 용도
    • 모든 행동을 수행하기 전에 ‘중재자 객체’의 결정이 있어야 하고, 중재자 객체로 프로그램이 수행됨
    • 각 객체들은 중재자만 알게됨
  • 사용 방법
    • 각 객체와 중재자를 연결함
  • Class Diagram

12. 방문자 패턴(Visitor Pattern)

  • 용도
    • 데이터와 메소드를 구분하기 위함
    • 많은 데이터에 여러 가지 유형의 처리를 수행할 경우 활용
  • 사용 방법
    • 데이터 구조 내부를 traversal하는 ‘visitor’ 클래스로 그 클래스에게 데이터의 처리를 맡김, 새로운 처리를 추가할 때는 새로운 visitor를 생성함
  • Class Diagram

13. 팩토리 메소드 패턴(Factory Method Pattern)

  • 용도
    • Instnce 작성을 하위 class에게 위임
      • Instance를 만드는 방법은 상위 class에서 결정하지만, 구체적인 class명을 결정하지 않음
    • Instance 생성을 위한 Framework과 실제 Instance를 생성하는 Class를 분리함
    • 객체를 만드는 공장을 만드는 패턴 -> 결합도가 낮아질 수 있다
  • 사용 방법
    • Factory객체를 만들고 Factory에서 객체들을 생성한다
  • Class Diagram
*****


'프로그래밍 > 디자인패턴' 카테고리의 다른 글

디자인패턴 요약  (0) 2018.06.11
디자인 패턴 요약  (0) 2018.06.11
쉽게 배우는 Template 패턴  (0) 2017.01.29
쉽게 배우는 Builder 패턴  (0) 2017.01.29
쉽게 배우는 Adapter 패턴 (아답터 패턴)  (0) 2017.01.29
블로그 이미지

낭만가을

,

디자인 패턴(Design Pattern) 이란

디자인 패턴이란 프로그래밍 할때에 문제를 해결하고자 코드의 구조들을 일정한 형태로 만들어 
재이용하기 편리하게 만든 일정한 패턴이라고 생각하시면 됩니다. 설명이 좀 어렵나요? 위키백과에는 다음과 같이 정의하고있습니다.


말하자면 구조적인 문제를 해결하는 방식을 이름을 붙여서 재이용하기 좋은 형태로 정리해둔 것이죠.


오늘 알아볼 GoF의 디자인 패턴은 위에도 있다시피 네명의 컴퓨터과학 연구자들이 소개한 대표적인 디자인패턴 방식입니다.


물론 아 대충 이런것이구나 는 이해가 금방될지라도 실제로 프로그래밍에 사용하려면 어려운점이 많아짐으로 

우선 대략적으로 설명을 해두고 나중에 하나씩 따로 포스팅하도록 하겠습니다.


디자인패턴을 사용할 때의 장,단점

장점
–개발자 간의 원활한 의사소통
–소프트웨어 구조 파악 용이
–재사용을 통한 개발 시간 단축
–설계 변경 요청에 대한 유연한 대처

단점
–객체지향 설계/구현 위주로 사용된다.

–초기 투자 비용 부담.


디자인패턴의 종류

1. 생성패턴

–Abstract Factory (추상 팩토리)  
 -동일한 주제의 다른 팩토리를 묶어 준다.
–Builder
 -생성(construction)과 표기(representation)를 분리해 복잡한 객체를 생성한다
–Factory Method
 -생성할 객체의 클래스를 국한하지 않고 객체를 생성한다.
–Prototype (원형)
 -기존 객체를 복제함으로써 객체를 생성한다.
–Singleton (단일체)
 -한 클래스에 한 객체만 존재하도록 제한한다.

2. 구조패턴

–Adapter (적응자)
 -인터페이스가 호환되지 않는 클래스들을 함께 이용할 수 있도록, 타 클래스의 인터페이스를 기존 인터페이스에 덧씌운다.
–Bridge (가교)
 -추상화와 구현을 분리해 둘을 각각 따로 발전시킬 수 있다.
–Composite (복합체)
 - 0개, 1개 혹은 그 이상의 객체를 묶어 하나의 객체로 이용할 수 있다.
–Decorator (장식자)
 -기존 객체의 매서드에 새로운 행동을 추가하거나 오버라이드 할 수 있다.
–Façade (퍼사드)
 -많은 분량의 코드에 접근할 수 있는 단순한 인터페이스를 제공한다.
–Flyweight (플라이급)
 -다수의 유사한 객체를 생성·조작하는 비용을 절감할 수 있다.
–Proxy (프록시)
 -접근 조절, 비용 절감, 복잡도 감소를 위해 접근이 힘든 객체에 대한 대역을 제공한다.

3. 행위패턴

–Chain of Responsibility (책임연쇄)
 -책임들이 연결되어 있어 내가 책임을 못 질 것 같으면 다음 책임자에게 자동으로 넘어가는 구조
–Command (명령)
 -위의 명령어를 각각 구현하는 것보다는 위 그림처럼 하나의 추상 클래스에 메서드를 하나 만들고 각 명령이 들어오면 그에 맞는 
  서브 클래스가 선택되어 실행하는 것
–Interpreter (해석자)
 -문법 규칙을 클래스화한 구조를 갖는SQL 언어나 통신 프로토콜 같은 것을 개발할 때 사용
–Iterator (반복자)
 -반복이 필요한 자료구조를 모두 동일한 인터페이스를 통해 접근할 수 있도록 메서드를 이용해 자료구조를 활용할 수 있도록 해준다.
–Mediator (중재자)
 -클래스간의 복잡한 상호작용을 캡슐화하여 한 클래스에 위임해서 처리 하는 디자인 패턴
–Memento (메멘토)
 -Ctrl + z 와 같은 undo 기능 개발할 때 유용한 디자인패턴. 클래스 설계 관점에서 객체의 정보를 저장
–Observer (감시자)
 -어떤 클래스에 변화가 일어났을 때, 이를 감지하여 다른 클래스에 통보해주는 것
–State (상태)
 -동일한 동작을 객체의 상태에 따라 다르게 처리해야 할 때 사용하는 디자인 패턴
–Strategy (전략)
 -알고리즘 군을 정의하고 각각 하나의 클래스로 캡슐화한 다음, 필요할 때 서로 교환해서 사용할 수 있게 해준다.
–Template Method
 -상위 클래스에서는 추상적으로 표현하고 그 구체적인 내용은 하위 클래스에서 결정되는 디자인 패턴
–Visitor (방문자)
 -각 클래스의 데이터 구조로부터 처리 기능을 분리하여 별도의 visitor 클래스로 만들어놓고 해당 클래스의 메서드가 
  각 클래스를 돌아다니며 특정 작업을 수행하도록 하는 것



참고 사항

GoF_의_디자인_패턴.pdf

       GoF_의_디자인_패턴.pdf



'프로그래밍 > 디자인패턴' 카테고리의 다른 글

디자인패턴 요약  (0) 2018.06.11
디자인패턴요약  (0) 2018.06.11
쉽게 배우는 Template 패턴  (0) 2017.01.29
쉽게 배우는 Builder 패턴  (0) 2017.01.29
쉽게 배우는 Adapter 패턴 (아답터 패턴)  (0) 2017.01.29
블로그 이미지

낭만가을

,


전체적인 로직에는 큰 차이가 없지만 일부분만 바뀌는 비스무레한 몇 가지 클래스가 있다고 칩시다. 일부분을 위해서 전체를 새로 작성할 필요는 없지요. Template Method에서는 전반적인 구현은 상위클래스(주로 Abstract로 만듭니다.)에서 담당하고 부분적인 곳의 구체적인 구현은 하위클래스가 담당합니다.


2. 예제


------------- 템플릿 메쏘드가 있는 Abstract Class ---------------

package ch04_TemplateMethod;


public abstract class Worker {

    protected abstract void doit();

    public final void work(){

        System.out.println("출근");

        doit();

        System.out.println("퇴근");

    }

}

------------- Abstract Class 구현체 1 ---------------------

package ch04_TemplateMethod;


public class Designer extends Worker {

    @Override

    protected void doit() {

        System.out.println("열심히 디자인");

    }

}

------------- Abstract Class 구현체 2 ---------------------

package ch04_TemplateMethod;


public class Gamer extends Worker {

    @Override

    protected void doit(){

        System.out.println("열심히 껨질");

    }

}

------------- 테스트 코드 ---------------------

package ch04_TemplateMethod;


public class Test {

    public static void main(String[] args) {

        Worker designer = new Designer();

        designer.work();

        Worker gamer = new Gamer();

        gamer.work();

    }

}


Worker 클래스의 work()는 내부적으로 abstract 메쏘드인 doit()을 호출하고 있습니다. work() 안에서 전반적인 로직이 수행되고, 로직 중 각각의 특성을 탈 수 있는 부분을 doit() 안에서 해결합니다. doit()은 실제 구현체에서 알아서 구현하면 됩니다.

work() 를 final로 구현한 것은 하위 클래스에서 전체적인 로직 변경을 하지 못하도록 하는 것입니다.


3. Template Method 사용시 고려사항


Template Method는 위험성을 어느 정도 내포하고 있습니다. 바로 전체적인 프로세스가 바뀌는 것입니다. 상위 클래스에서 변동이 일어날 경우 하위 클래스가 안전하리라는 보장은 할 수 없습니다. 상위 클래스에 abstract method가 하나만 추가되어도 모든 하위 클래스는 변경이 불가피합니다. 나중에 발생하는 작은 변경이 큰 재난을 일으킬 수 있습니다. 이것은 상속이 가지는 위험성입니다.

그래서 Template Method 패턴을 사용할 때는 상위클래스에 대한 심사숙고가 반드시 필요합니다. 일반적으로는 전체적인 프로세스를 담당하는 로직을 final 메쏘드로 정의하기도 하지만, 프로세스 자체의 변경을 고려해 상속의 여지를 남겨두기 위해 final 메쏘드로 정의하지 않기도 합니다.

또 한가지는 하위 클래스의 메쏘드들은 외부에서 직접 호출되지 않고 상위 클래스의 Template Method에서 호출됩니다. 그래서 주로 protected 로 선언됩니다. 그런 이유로 외부의 호출과 구체적인 구현체의 메쏘드가 실행되기까지의 과정을 쉽게 파악하기가 어렵습니다. 문제가 생겼을 때 추적이 어려울 수도 있다는 것이죠.


4. JAVA API에 있는 Template Method


아마 JDK안에 가장 많이 들어 있는 패턴 중 하나가 Template Method일 겁니다. 

Servlet 을 개발할 때, HttpServlet을 상속 받아 doGet() 과 doPost() 를 구현합니다. HttpServlet의 service() 에서 하위구현체의 doGet()이나 doPost() 등으로 분기를 시킵니다.(그 외에도 do머시기하는 메쏘드가 있지만 생략합니다.) Template Method의 전형적인 사용법 중 하나입니다. 분기를 담당하는 부분은 상위클래스에 구체적으로 구현하고, 분기된 이후의 행동은 하위구현체에 떠 넘기는 방법이죠.


HashSet이라는 Set의 구현체를 아시죠? 얘는 Set이니까 중복 데이터를 요소로 가지지 않습니다. 그럼 '같다 다르다'의 기준은 뭘까요? 내용이 같으면 될까요? 아니면, 실제 레퍼런스가 같아야 할까요?

이름에 나와 있듯 hash 값이 일단 같아야 합니다. hash값은 Object의 hashCode() 메쏘드를 이용하여 체크합니다. 그리고 나서 또 Object의 equals() 메쏘드를 호출합니다. 그래서 Set에 넣을 요소에 대해서는 hashCode() 메쏘드와 equals() 메쏘드가 잘 구현되어있어야 합니다. 그렇지 않으면, 중복된 데이터가 삽입될 수 있습니다.

HashSet의 경우는 위에서 설명한 Template Method와는 좀 다릅니다. 상위클래스와 하위클래스의 상관관계 같은 게 없죠. 다만 나도 모르는 사이에 내가 구현한 메쏘드가 호출될 수 있기 때문에 Template Method가 될 수 있습니다.(HashSet의 add(SomeClass) 메쏘드는 SomeClass의 hashCode()와 equals()를 호출합니다. )

정확히 말하면 Set.add(SomeClass) 메쏘드는 Set.contains(SomeClass) 메쏘드를 호출하고 그 안에서 다시 SomeClass.hashCode()와 SomeClass.equals(SomeClass) 를 호출합니다. ( 중간에 좀 더 복잡한 과정이 있지만, 설명할 필요는 없으므로 생략합니다. )

여기서 UI관련 각종 EventListener들도 그런 맥락에서 Template Method라고 볼 수 있습니다. event 발생에서 리스너까지의 과정을 알 필요가 없습니다. 대략 어떤 이벤트를 발생시키면, 어떤 이벤트 리스너한테 전달된다 정도만 알면 되죠. 이벤트 핸들링에는 그 외에도 여러가지 패턴들이 적용되어 있습니다.

블로그 이미지

낭만가을

,

1. Builder 패턴이란?


bulider pattern은 창조적 디자인 패턴(creational patter) 에 속합니다. 이것은 factory pattern 또는 abstract factory pattern과 매우 비슷합니다.

builder pattern은 선택적인 파라메터가 많을 경우 제공 상태를 일관성 있게 해주고, object를 생성시킬때 step-by-step으로 만들 수 있도록 제공해주며 최종에는 만들어진 object를 리턴한다



2. 예제


// Product 클래스 를 만들고 그안에 Builder 패턴을 사용하는 ProductBuilder 빌더를 만듭니다.
   

 //테스트
   

//결과
 



3. 자바에서 쓰이는 builder 패턴


java.lang.StringBuilder

은 대표적인 빌더 패턴이라고 볼수 있습니다.

시간이 되실때 소스를 보시면 많은 도움이 될것입니다.


블로그 이미지

낭만가을

,

1. Adapter 패턴이란


이미 구현되어 있는 코드가 있는데, 둘이 연결 좀 시켜주고 싶을 때가 있죠. 어떤 좋은 메서드가 있는데, 인자로 A라는 형식을 받습니다. 근데, 이미 구현되어 있는 코드에는 B라는 형식으로 구현되어 있습니다. 이럴 때, B를 A의 형식으로 바꿔주면 좋은 메서드를 써먹을 수 있습니다. Adapter 패턴은 어떤 오브젝트를 캐스팅이 불가능한 다른 클래스의 형태로 변환시켜주는 것입니다.


2. 따라하기


// Adapter Class


//test 클래스

 

 //결과 


우리가 최종적으로 쓰고자하는 것은 nextObject() 입니다. 그 녀석은 인자로 Enumeration을 받고 있지요. 

그러나 우리가 가지고 있는 것은 Iterator입니다. IteratorToEnumeration 클래스는 Iterator를 받아서 Enumeration 으로 변경시켜줍니다. 

A to B의 형태를 가지는 Adapter는 A를 멤버변수로 가지고 B를 구현합니다.

즉, IteratorToEnumeration 클래스가 이 역활을 하고 있습니다. IteratorToEnumeration 이클래스가 아답터 클래스 입니다.


3. JAVA API에 있는 Adapter 패턴 을 이용한 클래스들


이클립스나 인텔리 제이에서 저 소스들을 파헤쳐 가면서 어떻게 adapter 패턴들을 사용했는지 한번 살펴보시기 바랍니다.
시간이 될때 저도 저 클래스들이 apater 패턴을 사용하는가를 작성하겠습니다.


블로그 이미지

낭만가을

,

1. iterator 패턴이란


개발을 하면서  array나 List, Set, Map과 같은 interface 들을 많이 사용합니다. 이것들의 특징은 어떤 데이터들의 집합체라는 겁니다. 

원래 집합체란 게 속에 뭐가 들었냐가 중요하죠. 

그래서 집합체들을 다룰 때는 얘들이 가지고 있는 개별 원소에 대해서 이런 저런 작업들을 할 일이 많습니다. 

iterator를 쓰게 되면, 집합체와 개별 원소들간에 분리시켜 생각할 수가 있습니다. 심지어는 그 집합체가 어떤 클래스의 인스턴스인지 조차 신경쓰지 않아도 됩니다.


2. 예제

// iterator 인터페이스를 만든다.
   

// NameRepository 클래스를 iterator 인터페이스를 이용하게 만든다.
   

 // 테스트
   

 //결과
 



3. Iterator관련 interface


iterator  인터페이스를 만드는 대신에 구현되어 있는 java 의 iterable 인터페이스를 사용해도 됩니다.


private class NameIterator implements   Iterable<String> {

위와같은 식으로 구현되어 있는걸 사용해도 되지만 iterator  패턴이 어떤건지 알기 위하여 구현을 임의로 한것입니다.


4. JAVA API에 있는 Iterator


우리가 알고 있는 일반적인 집합체들은 전부 Iterator를 제공합니다. Set, List 등은 Collection 을 상속 받는데, Collection이 Iteratable을 상속 받기 때문입니다.

위에서 청록색 부분을 list.iterator() 라고 쭐여버려도 됩니다. 걍 있는 거 안 쓰고 굳이 구현한 건 예제 파일을 함 보여줄라고 한 겁니다. 사실은 예제 전체가 억지로 만들어낸 겁니다. 일반적인 집합체를 구현해서 쓰는 일은 거의 없고, JDK 안에 들어 있는 애들을 가져다 쓰는데, 걔들은 거의 대부분 Iterator를 제공하거든요.(Map은 한 다리 건너서 제공합니다.) 그래서 Iterator를 직접 구현할 일은 거의 없습니다. 가져다가 쓸 일이 있을 뿐이죠.


이제 Map은 왜 Iterator를 제공하지 않는 지를 살펴보죠. Map은 Set이나 List와는 달리 key-value의 구조입니다. key에 대한 Iterator인지 value에 대한 Iterator인지 구별할 방법이 없죠. 그래서 아예 제공을 안 합니다. 그러나 Map에는 key에 대해서는 Set<K> keySet()이라는 key를 Set으로 가져오기를 지원하고, value에 대해서는 Collection<V> values() 를 제공합니다. 위에서 말씀드렸다시피 Set과 Collection은 둘다 Iterator를 제공합니다.



블로그 이미지

낭만가을

,

1. Factory  패턴 이란


아주 중요한 패턴중에 하나 입니다. Factory 패턴은 creational pattern  에 속하는 패턴입니다.

Factory 패턴은 객체생성로직 없이 객체를 만들어 내는 패턴입니다.. 인터페이스를 통해 만들어진 객체를 참조 하죠.


쉽게 설명해드리겠습니다.  factory 는 한국어로 공장이란 뜻이죠.  즉 객체를 만들어내는 공장 입니다.  

객체 선언은 보통 new 객체() 이런식으로 하죠. factory는 내부에서 그런 일을 해줍니다. 즉 factory를 가져다가 쓰는 부분에서는 new 객체()와 같은 식으로 변수를 선언할 필요가 없습니다. Abstract class나 인터페이스에 대해서 다양한 하위 구현체가 있을 경우에 사용하면 좋습니다. 사용법은 Factory.create(인자는 맘대로) 와 같이 됩니다. 


실무에서 자주 쓰이는 패턴중 하나이니 아래와 같이 천천히 따라해보도록 하죠.


2. 따라하기


// animal 인터페이스를 만듭니다. 기본이 되는 interface 죠. 모든 디자인 패턴은 interface 를 사용한다 해도 과언이 아닙니다.


// Cat 클래스를 만듭니다.


// Cow 클래스를 만듭니다.


// Dog 클래스를 만듭니다.


// animal 을 만들어내는  AnimalFactory 클래스를 만든다. 

//( 이 class 가 핵심 입니다. factory 패턴을 구현한곳이죠. 이해하기 힘드시다면 이 class 만 30번 보시면 이해가 되실겁니다.)


// 자 테스트를 한번 해볼까요.

 

//결과


3. Factory 의 이해 

위의 결과와 같이 Animal interface 를 이용해서 각자 다른 소리를 내는 3개의 클래스를 만들어 봤습니다.

AnimalFactory 클래스에서는 각 동물들의 이름을 받아서 클래스를 만들어 냈습니다. 즉 팩토리 패턴을 구현해 놓은 클래스 입니다.


테스트를 실행하는 main 클래스 안에는 new 라는 구문 자체가 없습니다 팩토리 패턴은. 정확히 어떤 클래스의 인스턴스인지 신경쓰지 않고 구현할 수 있는 장점이 있습니다. 객체 타입이 굉장히 유연해 질 수 있죠.


이것으로 아주 쉽게 배우는 factory 패턴을 마치고자 합니다. 



블로그 이미지

낭만가을

,

수많은 디자인 패턴을 다 익히려면 시간이 많이 걸립니다. 혹은 공부한 디자인 패턴을 잊어버리곤 하죠

요점만 딱 암기 하고 있으면 다음에 디자인 패턴을 쓰고 싶을대  그 요점을 기준으로 다시 생각이 나게끔 아래와 같이 정리를 해봤습니다.


 하위클래스에게 위임하기

1. Iterator : 순서대로 지정해서 처리하기

2. Adapter : 바꿔서 재이용하기

3. Template Method : 하위 클래스에서 구체적으로 처리하기

4. Factory Method : 하위 클래스에서 인스턴스 만들기 


 인스턴스 만들기 

5. Singleton : 인스턴스를 한 개만 만들기

6. Prototype : 복사해서 인스턴스 만들기

7. Builder : 복잡한 인스턴스 조립하기

8. Abstract Factory : 관련 부품을 조합해서 제품 만들기

 분리해서 생각하기

9. Bridge : 기능계층과 구현 계층 분리하기

10. Strategy : 알고리즘을 모두 바꾸기

 동일시 하기

11. Composite : 그릇과 내용물을 동일시 하기

12. Decorator : 장식과 내용물을 동일시 하기

 구조를 돌아다니기

13. Visitor : 데이터 구조를 돌아다니면서 처리하기

14. Chain of Responsibility 책임 떠넘기기

 단순화하기

15. Facade : 단순한 창구

16. Mediator : 중개인을 통해서 처리하기

 상태를 관리하기

17. Observer : 상태의 변화를 알려주기

18. Memento : 상태를 저장하기

19. State : 상태를 클래스로 표현하기

 낭비 없애기

 20. Flyweight : 동일한 것을 공유해서 낭비 없애기 

21. Proxy : 필요해지면 만들기

 클래스로 표현하기

22. Comman : 명령을 클래스로 하기

23. Interpreter : 문법규칙을 클래스로 표현하기




블로그 이미지

낭만가을

,

http://stackoverflow.com/questions/1001767/what-is-the-basic-difference-between-the-factory-and-abstract-factory-patterns

블로그 이미지

낭만가을

,