設(shè)計(jì)模式系列-建造者模式
建造者模式用于將復(fù)雜對象的創(chuàng)建和表示分離,有些對象由很多部分組成,每個(gè)部分又可以有多種不同選擇,創(chuàng)建這種對象的時(shí)候往往需要考慮使用建造者模式。
舉個(gè)例子
一輛汽車由發(fā)動機(jī),方向盤,車燈,車燈,車身顏色等組成,每輛車的顏色,車輪大小,車燈樣式可能會不一樣,但是車的組成部分不會少。
建造模式有兩種實(shí)現(xiàn)方式,第一種方式是有導(dǎo)演的方式,第二種是無導(dǎo)演方式。根據(jù)我的經(jīng)驗(yàn)日常使用無導(dǎo)演的方式可能會更多一些。
有導(dǎo)演
所謂有導(dǎo)演就是通過一個(gè)導(dǎo)演類來指揮對象創(chuàng)建的過程,客戶端使用導(dǎo)演類來獲取對象,不用關(guān)心對象具體的創(chuàng)建過程。
先看一下UML圖,對建造模式有個(gè)大概的了解。
看一下具體代碼,我們以建造一輛汽車舉例
- public class Car {
- private String wheel;
- private String engine;
- private String seat;
- private String lamp;
- private String color;
- //篇幅原因,此處省略get,set方法
- @Override
- public String toString() {
- return "Car{" +
- "wheel='" + wheel + '\'' +
- ", engine='" + engine + '\'' +
- ", seat='" + seat + '\'' +
- ", lamp='" + lamp + '\'' +
- ", color='" + color + '\'' +
- '}';
- }
- }
抽象Builder類,指定建造復(fù)雜對象步驟
- public abstract class Builder {
- public abstract void buildWheel();
- public abstract void buildSeat();
- public abstract void buildLamp();
- public abstract void buildColor();
- public abstract void buildEngine();
- public abstract Car getCar();
- }
具體Builder類,實(shí)現(xiàn)復(fù)雜對象具體建造過程和內(nèi)容
- public class ConcreteBuilder extends Builder {
- private Car car;
- public ConcreteBuilder() {
- car = new Car();
- }
- @Override
- public void buildWheel() {
- car.setWheel("wheel");
- }
- @Override
- public void buildSeat() {
- car.setSeat("seat");
- }
- @Override
- public void buildLamp() {
- car.setLamp("lamp");
- }
- @Override
- public void buildColor() {
- car.setColor("color");
- }
- @Override
- public void buildEngine() {
- car.setEngine("engine");
- }
- //返回構(gòu)建好的汽車模型
- @Override
- public Car getCar() {
- return car;
- }
- }
Director類,決定了復(fù)雜對象的創(chuàng)建過程。
- public class CarDirector {
- public Car createCar(Builder builder){
- builder.buildWheel();
- builder.buildSeat();
- builder.buildLamp();
- builder.buildColor();
- builder.buildEngine();
- return builder.getCar();
- }
- }
客戶端這樣使用
- public class BuilderClient {
- public static void main(String[] args){
- CarDirector carDirector = new CarDirector();
- //通過Director創(chuàng)建具體對象,不關(guān)心對象的創(chuàng)建過程
- Car car = carDirector.createCar(new ConcreteBuilder());
- System.out.println(car.toString());
- }
- }
無導(dǎo)演
無導(dǎo)演模式感覺日常開發(fā)中用的比較多,但凡見到形似這樣的代碼,大概率就是建造者模式了。
- Car car = concreteBuilderA.buildEngine("engine")
- .buildLamp("lamp")
- .buildSeat("seat")
- .buildColor("color")
- //.buildWheel("wheel")
- .build();
老規(guī)矩先來看一下UML圖,來個(gè)整體的認(rèn)識。
同樣來看一下具體代碼實(shí)現(xiàn),還是以創(chuàng)建汽車為例,所以Car的代碼不在重復(fù)給出。
Builder類
- public abstract class BuilderA {
- //返回builder自身
- abstract BuilderA buildWheel(String wheel);
- abstract BuilderA buildEngine(String engine);
- abstract BuilderA buildLamp(String lamp);
- abstract BuilderA buildSeat(String seat);
- abstract BuilderA buildColor(String color);
- abstract Car build();
- }
具體Builder,負(fù)責(zé)對象的具體創(chuàng)建工作。
- public class ConcreteBuilderA extends BuilderA {
- private Car car;
- public ConcreteBuilderA() {
- car = new Car();
- }
- @Override
- BuilderA buildWheel(String wheel) {
- car.setWheel(wheel);
- return this;
- }
- @Override
- BuilderA buildEngine(String engine) {
- car.setEngine("engine");
- return this;
- }
- @Override
- BuilderA buildLamp(String lamp) {
- car.setLamp("lamp");
- return this;
- }
- @Override
- BuilderA buildSeat(String seat) {
- car.setSeat("seat");
- return this;
- }
- @Override
- BuilderA buildColor(String color) {
- car.setColor("color");
- return this;
- }
- @Override
- Car build() {
- return car;
- }
- }
客戶端這樣使用
- public class BuilderAClient {
- public static void main(String[] args){
- ConcreteBuilderA concreteBuilderA = new ConcreteBuilderA();
- Car car = concreteBuilderA.buildEngine("engine")
- .buildLamp("lamp")
- .buildSeat("seat")
- .buildColor("color")
- //.buildWheel("wheel")
- .build();
- System.out.println(car.toString());
- }
- }
總結(jié)
建造者模式是創(chuàng)建型模式之一,所謂的沒有Director的模式,只不過是把建造過程留給了客戶端,讓使用者自己決定怎樣創(chuàng)建對象。無Director模式的實(shí)現(xiàn)關(guān)鍵是Builder類里面構(gòu)建每個(gè)組件的方法都是返回Builder自己。