디자인 패턴 4분 읽기

팩토리 패턴

팩토리 패턴은 특정 인스턴스를 생성하는 클래스를 만들어 인스턴스의 생성과 기능 구현을 분리시킨 디자인 패턴이다.

팩토리 패턴

팩토리 패턴은 특정 인스턴스를 생성하는 클래스를 만들어 인스턴스의 생성과 기능 구현을 분리시킨 디자인 패턴이다.

인스턴스 생성을 담당하는 팩토리가 있기 때문에 클라이언트는 new키워드를 이용하여 인스턴스를 생성하지 않아도 된다.

이 의미는 클라이언트는 인스턴스 생성 방식을 몰라도 팩토리에 생성 요청만 한다면 인스턴스를 받을 수 있다는 것이다. 이렇게 되면 인스턴스 방식이 변하더라도 클라이언트 코드를 수정하는 것을 최소화할 수 있고, 인스턴스 생성에 변화는 팩토리를 수정하기만 해도 되기 때문에 팩토리 패턴을 사용하게 된다.

또한 인스턴스 생성을 팩토리 내부에서 해야 하기 때문에 팩토리 내부에서 분기문으로 처리하게 된다.

// 기능 구현부
class Animal {
  constructor(name, type) {
    this.name = name;
    this.type = type;
  }
  getName() {
    return this.name;
  }
  getType() {
    return this.type;
  }
}

class Cat extends Animal {}
class Dog extends Animal {}

// 팩토리
class AnimalFactory {
  typeMap = {
    cat: Cat,
    dog: Dog,
  };

  // 인스턴스 생성 함수
  create(props) {
    const Instance = this.typeMap[props.type];
    // 인스턴스 생성
    return new Instance(props.name, props.type);
  }
}

// 여기서 new는 원하는 인스턴스를 생성하는 것이 아니라 팩토리의 인스턴스를 생성한 것이다.
const cat1 = new AnimalFactory().create({
  name: "cat1",
  type: "cat",
});
console.log(cat1);

추상 팩토리

만들어야 할 컴포넌트를 추상적으로 정하고, 어떤 구체적인 상황이 주어지면 각 컴포넌트를 구체적으로 만드는 방식이다. 인터페이스에서는 서브 클래스들이 어떤 값을 가지고 있을 지 추상적으로 선언한다. 각 서브 클래스는 이에 맞게 객체를 생성해서 반환한다.

기존의 인스턴스 생성을 팩토리에서 하는 것이 아니라 생성하는 행위만 선언하고, 인스턴스 생성은 서브 클래스들이 공통된 메소드로 생성하는 방식이다.

// 기능 구현부
class Animal {
  constructor(name, type) {
    this.name = name;
    this.type = type;
  }
  getName() {
    return this.name;
  }
  getType() {
    return this.type;
  }
}

class Cat extends Animal {}
class Dog extends Animal {}

// 인스턴스를 생성할 서브 클래스
class CatFactory{
  static create(props){
    return new Cat(props.name, props.type);
  }
}
class DogFactory{
  static create(props){
    return new Dog(props.name, props.type);
  }
}

// 팩토리
class AnimalFactory {

  // 인스턴스 생성하는 행위
  static create(factory,props) {
    // 실제 인스턴스 생성은 각 서브 클래스에서 담당
    return factory.create(props);
   
  }
}

// 여기서 new는 원하는 인스턴스를 생성하는 것이 아니라 팩토리의 인스턴스를 생성한 것이다.
const cat1 = AnimalFactory.create(CatFactory,{
  name: "cat1",
  type: "cat",
});
console.log(cat1);

위 예제를 보면 AnimalFactory는 인스턴스를 생성하는 행위만 하고 실제 생성은 서브 클래스에게 위임했다. 이렇게 되면 팩토리 인터페이스가 의존성이 낮아지게 된다는 장점이 있다.