Builder Pattern là một mẫu thiết kế thuộc nhóm Creational Patterns (mẫu khởi tạo), được sử dụng để giải quyết vấn đề tạo ra các đối tượng phức tạp với nhiều thuộc tính mà không cần phải truyền quá nhiều tham số vào constructor hoặc tạo ra nhiều constructor với các tham số khác nhau (gọi là telescoping constructors problem).
public class Pizza {
private String size;
private boolean cheese;
private boolean pepperoni;
private boolean bacon;
// Telescoping constructors
public Pizza(String size) {
this.size = size;
}
public Pizza(String size, boolean cheese) {
this.size = size;
this.cheese = cheese;
}
public Pizza(String size, boolean cheese, boolean pepperoni) {
this.size = size;
this.cheese = cheese;
this.pepperoni = pepperoni;
}
public Pizza(String size, boolean cheese, boolean pepperoni, boolean bacon) {
this.size = size;
this.cheese = cheese;
this.pepperoni = pepperoni;
this.bacon = bacon;
}
}
Trong ví dụ trên, việc tạo ra nhiều constructor như vậy gây khó khăn khi muốn thêm các tùy chọn mới hoặc thay đổi logic.
Builder Pattern giải quyết các vấn đề trên bằng cách tách quá trình xây dựng đối tượng thành các bước riêng lẻ và cung cấp một cách tiếp cận tuần tự, dễ hiểu hơn. Thay vì truyền tất cả tham số vào một constructor hoặc tạo nhiều constructor khác nhau, bạn sử dụng một lớp Builder để tạo ra đối tượng.
Ví dụ với lớp Pizza, chúng ta có thể áp dụng Builder Pattern như sau:
public class Pizza {
private String size;
private boolean cheese;
private boolean pepperoni;
private boolean bacon;
// Private constructor chỉ được gọi từ Builder
private Pizza(PizzaBuilder builder) {
this.size = builder.size;
this.cheese = builder.cheese;
this.pepperoni = builder.pepperoni;
this.bacon = builder.bacon;
}
// Lớp Builder lồng bên trong lớp Pizza
public static class PizzaBuilder {
private String size;
private boolean cheese;
private boolean pepperoni;
private boolean bacon;
// Constructor của Builder với tham số bắt buộc
public PizzaBuilder(String size) {
this.size = size;
}
// Các phương thức để thêm các tùy chọn
public PizzaBuilder withCheese(boolean cheese) {
this.cheese = cheese;
return this;
}
public PizzaBuilder withPepperoni(boolean pepperoni) {
this.pepperoni = pepperoni;
return this;
}
public PizzaBuilder withBacon(boolean bacon) {
this.bacon = bacon;
return this;
}
// Phương thức build để tạo ra đối tượng Pizza
public Pizza build() {
return new Pizza(this);
}
}
}
Sử dụng Builder Pattern để tạo ra một đối tượng Pizza:
public class Main {
public static void main(String[] args) {
Pizza pizza = new Pizza.PizzaBuilder("Large")
.withCheese(true)
.withPepperoni(true)
.withBacon(false)
.build();
// Pizza với kích thước lớn, có phô mai và pepperoni, không có bacon
}
}
Builder Pattern là một giải pháp mạnh mẽ để khởi tạo các đối tượng phức tạp, giúp tăng tính rõ ràng và dễ bảo trì cho mã nguồn. Nó không chỉ giúp khắc phục vấn đề Telescoping Constructors, mà còn mang lại tính linh hoạt và dễ mở rộng trong quá trình phát triển phần mềm. Việc áp dụng đúng Builder Pattern sẽ giúp bạn kiểm soát tốt hơn quá trình khởi tạo các đối tượng, đồng thời giữ cho mã nguồn dễ hiểu và dễ bảo trì hơn.