设计模式之建造者模式
建造者模式(Builder Pattern)也叫作生成器模式,其定义如下:
Separate the construction process of a complex object from its representation so that the same construction process can create different representations.(将一个复杂的对象的构建与它的表示分离,使得同样的过程可以创建不同的表示。)
建造者模式的通用类图如下:
在建造者模式中,有如下4个角色:
- Product产品类
通常是实现了模板方法模式。 - Builder抽象建造者
提供一个接口,规范产品的组件,一般由子类实现。一般来说,产品的组成部分数与建造方法数相同,即有多少组成部分,就有多少个建造方法。 - ConcreteBuilder具体建造者
实现抽象类定义的所有方法,并返回一个组建好的对象。 - Director导演类
负责调用具体建造者按照顺序建造产品。导演只负责调度,真正执行的是具体的建造者。
举例
产品类,表示通过建造者模式创建的东西,通常它是一个组合或者继承(如模板方法)产生的类。简单示例如下:
public class Product {
private String part1;
private String part2;
public String getPart1() {
return part1;
}
public void setPart1(String part1) {
this.part1 = part1;
}
public String getPart2() {
return part2;
}
public void setPart2(String part2) {
this.part2 = part2;
}
@Override
public String toString() {
return "Product{" +
"part1='" + part1 + '\'' +
", part2='" + part2 + '\'' +
'}';
}
}
下面的是一个抽象的建造者,这个抽象的建造者可以是一个抽象类也可以是一个接口。示例如下:
public abstract class AbstractCarBuilder {
Product product = new Product();
abstract void buildPart1();
abstract void buildPart2();
public Product build() {
return product;
}
}
下面是具体的构建类。示例如下:
public class BenzCarBuilder extends AbstractCarBuilder {
@Override
public void buildPart1() {
System.out.println("建造奔驰车的第一部分");
product.setPart1("This is part one for benz");
}
@Override
public void buildPart2() {
System.out.println("建造奔驰车的第二部分");
product.setPart2("This is part two for benz");
}
}
public class BMWCarBuilder extends AbstractCarBuilder {
@Override
public void buildPart1() {
System.out.println("建造宝马的第一部分");
product.setPart1("This is part one for BMW");
}
@Override
public void buildPart2() {
System.out.println("建造宝马的第二部分");
product.setPart1("This is part two for BMW");
}
}
下面是导演类,指挥建造,也就是指挥建造的顺序。示例如下:
public class Director {
private AbstractCarBuilder carBuilder;
public Director(AbstractCarBuilder carBuilder) {
this.carBuilder = carBuilder;
}
public Product construct() {
carBuilder.buildPart1();
carBuilder.buildPart2();
return carBuilder.build();
}
}
然后是一个客户端来使用建造者模式建造车。实例如下:
public class Client {
public static void main(String[] args) {
BenzCarBuilder benzCarBuilder = new BenzCarBuilder();
Director director = new Director(benzCarBuilder);
Product product = director.construct();
System.out.println(product);
}
}
建造者模式的优缺点
建造者模式的优点
- 封装性
降低代码的耦合度。使用建造者模式客户端可以不必知道产品的内部组成细节是如何实现的。 - 建造者独立,容器扩展
各个建造者之间相互独立,方便扩展。例如BenzCarBuilder
和BMWCarBuilder
是相互独立的。 - 便于风险控制
由于具体建造者是相互独立的,因此可以对建造的过程逐步细化,而不对其他模块产生影响。
建造者模式的缺点
一定的使用范围,前面也提到了产品类建议使用模板方法,所以建造者模式的产品的组件基本相同,如果产品差异较大,建造者模式就不适用了。