- 빌더패턴이란

첫번째 점층적 생성자 패턴
public class User { private int userIdx; // 선택 private String name; // 필수 private String part; // 필수 private int age; // 선택 private String email; // 선택 }
여러개의 생성자를 따로 만들어야 한다. 지저분해지고 복잡해지는 단점이 있다.
public class User {
private int userIdx;
private String name;
private String part;
private int age;
private String email;
//만약 필드값이 더 많아지면 경우의 수는 더욱더 많아 질것이다.
public User(String name, String part) {
this.name = name;
this.part = part;
}
public User(int userIdx, int age, String email) {
this.userIdx = userIdx;
this.age = age;
this.email = email;
}
}
- 인자값의 순서도 중요해서 헷갈릴수도있다.
User user = new User(1, "이름", "파트", 25, "이메일");
- 이러한 단점을 보완하기 위해 setter 메소드를 사용한 자바 빈(Bean) 패턴이 고안되었다.
TourPlan tourPlan = new TourPlan();
tourPlan.setTitle("칸쿤 여행");
tourPlan.setNights(2);
tourPlan.setDays(3);
tourPlan.setStartDate(LocalDate.of(2020, 12, 9));
tourPlan.setWhereToStay("리조트");
tourPlan.addPlan(0, "체크인 이후 짐풀기");
tourPlan.addPlan(0, "저녁 식사");
tourPlan.addPlan(1, "조식 부페에서 식사");
tourPlan.addPlan(1, "해변가 산책");
tourPlan.addPlan(1, "점심은 수영장 근처 음식점에서 먹기");
tourPlan.addPlan(1, "리조트 수영장에서 놀기");
tourPlan.addPlan(1, "저녁은 BBQ 식당에서 스테이크");
tourPlan.addPlan(2, "조식 부페에서 식사");
tourPlan.addPlan(2, "체크아웃");
한번의 호출로 생성이 안되고, immutable 객체를 생성할 수 없다. (객체가 변할 여지가 존재한다)
이를 해결하기 위해서 빌더패던이 고안되었다.
빌더패던 만들어보기
Builder- 인스턴스 생성을 위한 api를 선언
Builder 코드
public interface TourPlanBuilder { TourPlanBuilder nightsAndDays(int nights, int days); TourPlanBuilder title(String title); TourPlanBuilder startDate(LocalDate localDate); TourPlanBuilder whereToStay(String whereToStay); TourPlanBuilder addPlan(int day, String plan); TourPlan getPlan(); }
ConcreateBuilder- Builder를 구현하는 역할
ConcreateBuilder 코드
public class DefaultTourBuilder implements TourPlanBuilder { private String title; private int nights; private int days; private LocalDate startDate; private String whereToStay; private List<DetailPlan> plans; @Override public TourPlanBuilder nightsAndDays(int nights, int days) { this.nights = nights; this.days = days; return this; } @Override public TourPlanBuilder title(String title) { this.title = title; return this; } @Override public TourPlanBuilder startDate(LocalDate startDate) { this.startDate = startDate; return this; } @Override public TourPlanBuilder whereToStay(String whereToStay) { this.whereToStay = whereToStay; return this; } @Override public TourPlanBuilder addPlan(int day, String plan) { if (this.plans == null) { this.plans = new ArrayList<>(); } this.plans.add(new DetailPlan(day, plan)); return this; } @Override public TourPlan getPlan() { //여기서 검증 로직 넣기 가능 return new TourPlan(title, nights, days, startDate, whereToStay, plans); } }
Direator- Builder 패턴을 이용하여 인스턴스 생성
Direator 코드
public class TourDirector { private TourPlanBuilder tourPlanBuilder; public TourDirector(TourPlanBuilder tourPlanBuilder) { this.tourPlanBuilder = tourPlanBuilder; } public TourPlan cancunTrip() { return tourPlanBuilder.title("칸쿤 여행") .nightsAndDays(2, 3) .startDate(LocalDate.of(2020, 12, 9)) .whereToStay("리조트") .addPlan(0, "체크인하고 짐 풀기") .addPlan(0, "저녁 식사") .getPlan(); } public TourPlan longBeachTrip() { return tourPlanBuilder.title("롱비치") .startDate(LocalDate.of(2021, 7, 15)) .getPlan(); } }
최종 사용 코드
public class App {
public static void main(String[] args) {
//빌더를 먼저 생성 해준다.
TourDirector director = new TourDirector(new DefaultTourBuilder());
TourPlan tourPlan = director.cancunTrip();
TourPlan tourPlan1 = director.longBeachTrip();
System.out.println(tourPlan.toString());
}
}
빌더패턴의 장단점
- 장점
- 각 인자를 파악하기가 쉽다.
- 객체의 일관성이 깨지지 않는다.
- Builder의 함수를 마지막에 이용함으로써 객체 검증이 가능하다.
- 복잡한 객체를 만드는 구체적인 과정을 숨길 수 있다.
- 단점
- 디렉터라는 객체를 클라이언트 쪽에서 생성을 해줘야한다.
- 빌더 디렉터 까지 만들어야하기때문에 구조가 복잡해 질수있다.
- 장점
자바에서 제공하는 빌더패턴
StringBuilder
StringBuilder stringBuilder = new StringBuilder(); String result = stringBuilder.append("whiteship").append("keesun").toString(); System.out.println(result);
스프링에서 제공하는 빌더 패턴
public static void main(String[] args) {
UriComponents howToStudyJava = UriComponentsBuilder.newInstance()
.scheme("http")
.host("www.whiteship.me")
.path("java playlist ep1")
.build().encode();
System.out.println(howToStudyJava);
}
'디자인 패턴' 카테고리의 다른 글
[디자인패턴] 싱글톤(Singleton) 패턴 (0) | 2022.04.10 |
---|---|
[디자인패턴] 팩토리(Factory)패턴 (0) | 2022.04.08 |
커맨드 패턴 (0) | 2021.12.21 |