设计模式-05-建造者模式
个人github地址:HibisciDai
设计模式系列项目源码:HibisciDai/DesignPattern-LearningNotes-HibisciDai
processon在线UML类图:processon
[TOC]
设计模式-05-建造者模式
建造者模式(Builder Pattern)
意图
将一个复杂对象的创建与表示分离,使得同样的创建过程可用不同的表示。
主要解决
主要解决在软件系统中,有时候面临着”一个复杂对象”的创建工作,其通常由各个部分的子对象用一定的算法构成;由于需求的变化,这个复杂对象的各个部分经常面临着剧烈的变化,但是将它们组合在一起的算法却相对稳定。
何时使用
一些基本部件不会变,而其组合经常变化的时候。
关键代码
建造者:创建和提供实例。
导演:管理建造出来的实例的依赖关系。
如何解决
将变与不变分离开。
应用实例
- 去肯德基,汉堡、可乐、薯条、炸鸡翅等是不变的,而其组合是经常变化的,生成出所谓的”套餐”。
- JAVA 中的 StringBuilder。
优点
当一个产品族中的多个对象被设计成一起工作时,它能保证客户端始终只使用同一个产品族中的对象。
缺点
注意事项
与工厂模式的区别是:建造者模式更加关注与零件装配的顺序。
案例1
杯子构造过程。
类图
代码
pattern05.bulider.demo1
1 2 3 4 5 6 7 8 9 10 11 12 13 14 15 16 17 18 19 20 21 22 23 24 25 26 27 28 29 30 31 32 33 34 35 36 37 38 39 40 41 42 43 44 45 46 47 48 49 50 51 52 53 54 55 56 57 58 59 60 61 62
| public class Director { void create(MyBulider b) { b.BuliderString(); b.BuliderCup(); b.BuliderBody(); b.getResult(); } }
public abstract class MyBulider { String myString; String myCup; String myBody;
abstract void BuliderString();
abstract void BuliderCup();
abstract void BuliderBody();
void getResult() { System.out.println(myString); System.out.println(myCup); System.out.println(myBody); } }
public class GlassCupBulider extends MyBulider {
@Override void BuliderString() { this.myString = "GlassCup-String"; }
@Override void BuliderCup() { this.myCup = "GlassCup-Cup"; }
@Override void BuliderBody() { this.myBody = "GlassCup-Body"; } }
public class SportCupBulider extends MyBulider {
@Override void BuliderString() { this.myString = "SportCup-String"; }
@Override void BuliderCup() { this.myCup = "SportCup-Cup"; }
@Override void BuliderBody() { this.myBody = "SportCup-Body"; } }
|
目标对象:
1 2 3 4 5 6 7 8 9 10 11 12 13 14 15 16 17 18 19 20 21 22 23 24 25 26 27 28 29 30 31 32 33
| public class Cup { String CupString; String Cup; String CupBody;
public String getCupString() { return CupString; }
public void setCupString(String cupString) { CupString = cupString; }
public String getCup() { return Cup; }
public void setCup(String cup) { Cup = cup; }
public String getCupBody() { return CupBody; }
public void setCupBody(String cupBody) { CupBody = cupBody; }
void drink() { System.out.println(CupString + Cup + CupBody); } }
|
测试输出
1 2 3 4 5 6 7 8 9 10 11
| public class Main { public static void main(String[] args) { Director d1 = new Director(); MyBulider mb1 = new SportCupBulider(); d1.create(mb1);
Director d2 = new Director(); MyBulider mb2 = new GlassCupBulider(); d2.create(mb2); } }
|
1 2 3 4 5 6
| SportCup-String SportCup-Cup SportCup-Body GlassCup-String GlassCup-Cup GlassCup-Body
|
案例2
对话框构建过程。
类图
代码
pattern05.bulider.demo2
1 2 3 4 5 6 7 8 9 10 11 12 13 14 15 16 17 18 19 20 21 22 23 24 25 26 27 28 29 30 31 32 33 34 35 36 37 38 39 40 41 42 43 44 45 46 47 48 49 50 51 52 53 54 55 56 57 58 59 60 61 62 63 64 65 66 67 68
| public abstract class MyBulider { String title; String icon; String message;
abstract void BuliderTitle();
abstract void BuliderIcon();
abstract void BuliderMessage();
void getResult() { System.out.println(title); System.out.println(icon); System.out.println(message); } }
public class Conform extends MyBulider {
@Override void BuliderTitle() { title = "Conform-title"; }
@Override void BuliderIcon() { icon = "Conform-icon"; }
@Override void BuliderMessage() { message = "Conform-message"; } }
public class Information extends MyBulider {
@Override void BuliderTitle() { title = "Information-title"; }
@Override void BuliderIcon() { icon = "Information-icon"; }
@Override void BuliderMessage() { message = "Information-message"; } }
public class Director { MyBulider mb;
Director(MyBulider mb) { this.mb = mb; }
void create() { mb.BuliderIcon(); mb.BuliderMessage(); mb.BuliderTitle(); mb.getResult(); } }
|
构建对象
1 2 3 4 5 6 7 8 9 10 11 12 13 14 15 16 17 18 19 20 21 22 23 24 25 26 27 28 29
| public class Diolog { String title; String icon; String message;
public String getTitle() { return title; }
public void setTitle(String title) { this.title = title; }
public String getIcon() { return icon; }
public void setIcon(String icon) { this.icon = icon; }
public String getMessage() { return message; }
public void setMessage(String message) { this.message = message; } }
|
测试输出
1 2 3 4 5 6 7 8 9 10 11
| public class Main { public static void main(String[] args) { MyBulider mb1 = new Conform(); Director d1 = new Director(mb1); d1.create();
MyBulider mb2 = new Information(); Director d2 = new Director(mb2); d2.create(); } }
|
1 2 3 4 5 6
| Conform-title Conform-icon Conform-message Information-title Information-icon Information-message
|
补充
Bulider
限定名在java中有指定类,代码例中更改为MyBulider
。
对于Builder
中引用指定对象需要打破封装,即透视目标构建配件的结构,并声明为自己的成员变量,即目标对象与建造者有相同的成员变量。
关于两个案例中Director
类构造有些不同导致方法调用有不一样。
案例一
1 2 3 4 5 6 7 8
| public class Director { void create(MyBulider b) { b.BuliderString(); b.BuliderCup(); b.BuliderBody(); b.getResult(); } }
|
案例二
1 2 3 4 5 6 7 8 9 10 11 12 13 14
| public class Director { MyBulider mb;
Director(MyBulider mb) { this.mb = mb; }
void create() { mb.BuliderIcon(); mb.BuliderMessage(); mb.BuliderTitle(); mb.getResult(); } }
|