builder模式

一。定义
  将一个复杂对象的构建与它的表示分离,使同样的构建过程可以创建不同的表示
      builder模式是一步一步创建一个复杂对象,允许用户在不知道内部构建细节的情况下,更精细的控制对象的构建过程。
二。使用场景
  相同的方法,不同的执行顺序,产生不同的时间结果时
  多个部件或零件,都可以装配到一个对象中,但是产生的运行结果又不相同时
  产品类非常复杂,或者产品类中的调用顺序不同产生了不同的作用,这个时候使用构造者模式非常合适
  当初始化一个对象特别复杂,如参数比较多,且很多参数都具有默认值时
三。builder模式的实现
**************************************************************************************
package com.yinazh.designpattern.builder;

public abstract class Computer{
protected String mBoard;
protected String mDisplay;
protected String mOS;

protected Computer(){}

public void setBoard(String board){
this.mBoard = board;
}

public void setDisplay(String display){
this.mDisplay = display;
}

public abstract void setOS();

public String toString(){
return "Computer{mBoard = " + mBoard + ", mDisplay = " + mDisplay + ", mOS = " + mOS;
}
}

public class MacBook extends Computer{
protected MacBook(){}
public void setOS(){
mOS = "Mac OS"
}
}

public abstract class Builder{
public abstract void buildBoard(String board);
public abstract void buildDisplay(String display);
public abstract void buildOS();
public abstract Computer create();
}

public class MacbookBuilder extends Builder{
private Computer mComputer = new MacBook();
public void buildBoard(String board){
mComputer.setBoard(board);
}
public void buildDisplay(String display){
mComputer.setDisplay(display);
}
public void buildOS(){
mComputer.setOS();
}
public Computer create(){
return mComputer;
}
}

public class Director{
Builder mBuilder = null;
public Director(Builder builder){
mBuilder = builder;
}
public void construct(String board, String display){
mBuilder.buildBoard(board);
mBuilder.buildDisplay(display);
mBUilder.buildOS();
}
}

public class Test{
pubilc static void main(String[] args){
Builder builder = new MacbookBuilder();
Director pcDirector = new Director(builder);
pcDirector.construct("aaaaaaa", "bbbbbb");
System.out.println("Computer Info = " + builder.create().toString());
}
}
**************************************************************************************
上述示例中,通过具体的MacbookBuidler来构建Macbook对象,而Director封装了构建复杂产品对象的过程,对外隐藏构建细节。Builder与Director一起将一个复杂对象的构建与它的表示分离,是的同样的狗年过程可以创建不同的对象。
 值得注意的是,在现实的开发中,Director角色经常是省略的,而直接使用一个Builder来进行对象的组装,这个Builder通常为链式调用,它的关键点是每个setter方法都返回自身,也就是return this,这样就使得setter方法可以链式调用,具体示例如下:
**************************************************************************************
package com.yinazh.designpattern;

//实现成员Weapon
public enum Weapon {
DAGGER, SWORD, AXE, WARHAMMER, BOW;
@Override
public String toString() {
return name().toLowerCase();
}
}

//实现成员Armor
public enum Armor {
CLOTHES("clothes"), LEATHER("leather"), CHAIN_MAIL("chain mail"), PLATE_MAIL("plate mail");
private String title;
Armor(String title) {
this.title = title;
}

@Override
public String toString() {
return title;
}
}


public enum HairColor {

WHITE, BLOND, RED, BROWN, BLACK;

@Override
public String toString() {
return name().toLowerCase();
}

}

public enum HairType {
BALD("bald"), SHORT("short"), CURLY("curly"), LONG_STRAIGHT("long straight"), LONG_CURLY("long curly");
private String title;
HairType(String title) {
this.title = title;
}

@Override
public String toString() {
return title;
}
}

public enum Profession {

WARRIOR, THIEF, MAGE, PRIEST;

@Override
public String toString() {
return name().toLowerCase();
}
}

//实现复杂产品类,类中使用静态内部类实现简化builder模式,在构建产品的时候,可以链式构建
public final class Hero {

private final Profession profession;
private final String name;
private final HairType hairType;
private final HairColor hairColor;
private final Armor armor;
private final Weapon weapon;

private Hero(Builder builder) {
this.profession = builder.profession;
this.name = builder.name;
this.hairColor = builder.hairColor;
this.hairType = builder.hairType;
this.weapon = builder.weapon;
this.armor = builder.armor;
}

public Profession getProfession() {
return profession;
}

public String getName() {
return name;
}

public HairType getHairType() {
return hairType;
}

public HairColor getHairColor() {
return hairColor;
}

public Armor getArmor() {
return armor;
}

public Weapon getWeapon() {
return weapon;
}

@Override
public String toString() {

StringBuilder sb = new StringBuilder();
sb.append("This is a ")
.append(profession)
.append(" named ")
.append(name);
if (hairColor != null || hairType != null) {
sb.append(" with ");
if (hairColor != null) {
sb.append(hairColor).append(' ');
}
if (hairType != null) {
sb.append(hairType).append(' ');
}
sb.append(hairType != HairType.BALD ? "hair" : "head");
}
if (armor != null) {
sb.append(" wearing ").append(armor);
}
if (weapon != null) {
sb.append(" and wielding a ").append(weapon);
}
sb.append('.');
return sb.toString();
}

/**
*
* The builder class.
*
*/
public static class Builder {

private final Profession profession;
private final String name;
private HairType hairType;
private HairColor hairColor;
private Armor armor;
private Weapon weapon;

/**
* Constructor
*/
public Builder(Profession profession, String name) {
if (profession == null || name == null) {
throw new IllegalArgumentException("profession and name can not be null");
}
this.profession = profession;
this.name = name;
}

public Builder withHairType(HairType hairType) {
this.hairType = hairType;
return this;
}

public Builder withHairColor(HairColor hairColor) {
this.hairColor = hairColor;
return this;
}

public Builder withArmor(Armor armor) {
this.armor = armor;
return this;
}

public Builder withWeapon(Weapon weapon) {
this.weapon = weapon;
return this;
}

public Hero build() {
return new Hero(this);
}
}
}

//测试
public class App {
public static void main(String[] args) {

Hero mage =new Hero.Builder(Profession.MAGE, "Riobard").withHairColor(HairColor.BLACK)
.withWeapon(Weapon.DAGGER).build();

Hero warrior =new Hero.Builder(Profession.WARRIOR, "Amberjill").withHairColor(HairColor.BLOND)
.withHairType(HairType.LONG_CURLY).withArmor(Armor.CHAIN_MAIL).withWeapon(Weapon.SWORD)
.build();

Hero thief =new Hero.Builder(Profession.THIEF, "Desmond").withHairType(HairType.BALD)
.withWeapon(Weapon.BOW).build();
}
}
**************************************************************************************
四。在android中的应用
  常见的使用builder模式的,就是AlertDialog的创建。
五。优缺点
优点: 良好的封装性,使用建造者模式可以使客户端不必知道产品内部的组成细节
缺点:会产生多余的Builder对象以及Director对象,消耗内存。
  • 0
    点赞
  • 0
    收藏
    觉得还不错? 一键收藏
  • 0
    评论

“相关推荐”对你有帮助么?

  • 非常没帮助
  • 没帮助
  • 一般
  • 有帮助
  • 非常有帮助
提交
评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值