✍️ 빌더 패턴, 장점
빌더 패턴의 첫 번째 장점으로, 생성 과정이 복잡한 인스턴스를 일관된 프로세스로 생성할 수 있다. 동시에 클라이언트가 빌더의 메서드를 체이닝 형태로 호출하며 자연스럽게 인스턴스를 구성하고 최종적으로 객체를 생성하도록 유도할 수 있다.
Student kangworld = new Student
.StudentBuilder(32140033)
.setName("kangworld")
.setPhoneNumber("010-1234-5678")
.setGrade("sophomore")
.getStudent();
두 번째 장점으로, 멤버 변수의 초기화와 검증을 각각의 멤버 변수별로 분리해서 작성할 수 있다. 가령 멤버 변수의 초기화를 검증하는 로직이 하나의 생성자에 다 포함되었다면 생성자의 크기가 비대해질 것이다.
아래와 같이 생성자에 초기화 검증 코드를 다 때려 박는 것보다
public class Student {
private int id;
private String name;
private String grade;
private String phoneNumber;
public Student(int id, String name, String grade, String phoneNumber) {
if (!grade.equals("freshman") && !grade.equals("sophomore")
&& !grade.equals("junior") && !grade.equals("senior")) {
throw new IllegalArgumentException(grade);
}
if (!phoneNumber.startsWith("010")) {
throw new IllegalArgumentException(phoneNumber);
}
this.id = id;
this.name = name;
this.grade = grade;
this.phoneNumber = phoneNumber;
}
}
빌더의 각각의 메서드에서 검증 과정을 분담하는 것이 유지 보수에 유리할 것이다.
public static class StudentBuilder {
private int id;
private String name;
private String grade;
private String phoneNumber;
public StudentBuilder(int id) {
this.id = id;
}
public StudentBuilder setName(String name) {
this.name = name;
return this;
}
public StudentBuilder setGrade(String grade) {
if (!grade.equals("freshman") && !grade.equals("sophomore")
&& !grade.equals("junior") && !grade.equals("senior")) {
throw new IllegalArgumentException(grade);
}
this.grade = grade;
return this;
}
public StudentBuilder setPhoneNumber(String phoneNumber) {
if (!phoneNumber.startsWith("010")) {
throw new IllegalArgumentException(phoneNumber);
}
this.phoneNumber = phoneNumber;
return this;
}
public Student getStudent() {
return new Student(this);
}
}
세 번째 장점으로, 디렉터를 사용하면 인스턴스를 만드는 구체적인 과정을 디렉터로 숨기고 클라이언트 코드는 디렉터를 호출함으로써 코드가 간결해지는 장점이 있다.
네 번째 가장 중요한 장점인데, 서로 다른 빌더 구현체를 주입함으로써 동일한 프로세스에서 서로 다른 객체를 생성할 수 있다.
가령 TourPlan을 상속받은 VipTourPlan과 VVipTourPlan이 있고, VipTourBuilder의 getPlan은 VipTourPlan을 반환하고 VVipTourBuilder는 VVipTourPlan을 반환한다고 가정하면 동일한 프로세스로 인스턴스를 생성하되 주입된 빌더에 따라 서로 다른 객체를 생성할 수 있게 된다.
public class TourDirector {
private TourPlanBuilder builder;
public TourDirector(TourPlanBuilder builder) {
this.builder = builder;
}
public TourPlan jejuTripPlan() {
return builder.title("제주도 여행")
.nightsAndDays(2, 3)
.startDate(LocalDate.of(2020, 12, 9))
.whereToStay("리조트").addPlan(0, "체크인")
.addPlan(0, "한라산 등반")
.addPlan(1, "한라봉 먹기")
.addPlan(2, "흑돼지 먹기")
.addPlan(3, "귀가")
.getPlan();
}
}
🍊 빌더 패턴, 단점
빌더 패턴의 단점으로, 클라이언트는 구체적인 인스턴스를 생성하기 전에 반드시 빌더를 생성해야 한다.
또 다른 단점으로 여느 디자인 패턴이 가지는 단점으로 관리해야 할 클래스가 많아지고 구조가 복잡해지는 단점이 있다.
인프런의 백기선님의 강의 코딩으로 학습하는 GoF의 디자인 패턴을 참고해서 작성했습니다.
'Java > Design Pattern with Java' 카테고리의 다른 글
[객체 생성 패턴] Chapter 5-1. Prototype Pattern : 패턴 소개 (0) | 2022.05.24 |
---|---|
[객체 생성 패턴] Chapter 4-5. Builder Pattern : Java와 Spring에서 찾아보는 빌더 패턴 (0) | 2022.05.16 |
[객체 생성 패턴] Chapter 4-3. Builder Pattern : 심플 빌더 (0) | 2022.05.12 |
[객체 생성 패턴] Chapter 4-2. Builder Pattern : 패턴 적용하기 (0) | 2022.05.09 |
[객체 생성 패턴] Chapter 4-1. Builder Pattern : 패턴 소개 (0) | 2022.05.08 |