Builder 빌더

고승원·2022년 10월 24일
1

Design Pattern

목록 보기
5/5

복잡한 객체를 단계별로 구성할 수 있다. 동일한 구성의 코드로 객체의 다양한 유형과 표현을 생성할 수 있다.

사용처

  • 생성자에 인자가 많을 때
  • 생성자에 매개변수가 많을 때

장점

  • 객체를 단계별로 구성하거나, 재귀적으로 단계를 구성할 수 있다.
  • 객체를 다양하게 구성할 때 동일 코드를 재사용할 수 있다.
  • SRP

단점

  • 여러개의 새로운 클래스를 생성해야 한다.

구현

Builder : 모든 유형의 빌더에 공통적인 구성단계 선언

Concreate Builder : Builder의 다양한 구현을 제공, 공통 인터페이스를 따르지 않는 제품 생산 가능

Product : 결과 객체. 다른 빌더에 의해 생성된 객체는 동일한 클래스 계층 또는 인터페이스에 속할 필요가 없다.

Director : 구성 단계를 호출하는 순서를 정의한다. 재사용 가능

Client : 빌더 객체중 하나와 Director를 연결해야 한다. 보통은 생성자 주입을 통해 한 번만 수행되지만, 특별한 상황에서는 매번 다른 빌더를 사용할 수 있다.

  1. 사용 가능한 모든 제품의 공통 구성단계를 명확히 정의한다. 그렇지 않으면 패턴 구현이 힘들다.
  2. 1 에서 정의된 내용으로 Builder Interface를 만든다.
  3. ConcreateBuilder를 구현한다. 이 때 getResult 메서드를 잊지 말자.
  4. Director 클래스를 생성한다. 한 빌더 객체를 사용하면 캡슐화 하기 쉬워진다.
  5. Client는 builder, director 객체 모두 생성한다. 생성된 builder객체는 director에게 전달해야 한다.
  6. 모든 제품이 동일한 인터페이스를 따르는 경우 director로부터 리턴받을 수 있다. 그렇지 않다면 빌더객체로부터 리턴받는다.

코드

Builder

interface Builder {
    void reset()
    void setRoof()
    void setWall()
}

ConcreateBuilder

class HouseBuilder implements Builder {
    private House house;

    public HouserBuilder() {  //생성자에서 초기화
        this.reset();
    }

    public void reset() {
        this.house = new House();
    }

    public void setRoof(...) {
        //지붕 구현
    }

    public void setWall(...) {
        //벽 구현
    }

    public House getProduct() {
        product = this.house;
        this.reset()
        return product;
    }

Director

class Director {
    
    public constructHouse(Builder builder) {
        builder.reset();
        builder.setRoof(...);
        builder.setwall(...);
    }

    public constructVilla(Builder builder) {
        ...
    }

Client

class Main {
    void makeHouse() {
        Director director = new Director();

        HouseBuilder builder = new HouserBuilder();
        director.constructHouse(builder);
        House house = builder.getProduct();

        VillaBuilder builder = new VillaBuilder()
        director.constructHouse(builder);
    }

이 방법 외에도 ConcreateBuilder에서 메서드 체이닝 방식으로 만들어도 된다.

메서드 체이닝, 롬복 방식을 사용하는 예제를 다루는 블로그를 참고하자

빌더 패턴은 복잡한 객체를 단계별로 구성하는데 중점을 둔다.

추상 팩토리와 구성은 비슷하지만 비슷한 객체군을 생성하는 추상 팩토리와 목적이 다르다.

빌더 패턴은 싱글톤으로 구현할 수 있다.

profile
봄은 영어로 스프링

0개의 댓글