实例探索Java模式之路——建造模式

来源:互联网 发布:淘宝违规12分 编辑:程序博客网 时间:2024/05/01 20:36
建造模式


1、建造模式是对象的创建模式。
建造模式是把一个产品的内部表象与产品的生产过程分割开来,从而使一个建造过程生产具有不同的内部表象的产品对象。


建造模式就比如汽车销售公司想要造汽车(相当于客户端),然后找到了汽车生产商(导演者),而在造汽车的过程中。生产商不是自己造汽车的各个零件,而是从其他国家购买零件,生产这个零件的具体国家就是具体的建造者,(导演者调用这些零件)然后把这些零件组合在一起就生产出来了一辆汽车,这就是建造模式。(个人理解)


2、


该系统产品product只有两个零件,Part1和part2。建造方法有两个。


抽象建造者:规范产品对象的各个组成部分的建造,模式中直接创建产品的对象的是具体建造者,具体建造者必须实现这个接口所要求的两个方法,另一种是结果返还方法。一般来说,产品所包含的零件数目与建造方法的数目相符。

具体建造者:与应用程序紧密相关。完成任务:1、实现抽象建造者,一步步地完成创建产品实例的操作。2、建造完成,提供产品实例。

导演者:调用具体建造者以创建产品对象。导演者角色没有产品类的具体知识,真正拥有产品类的具体知识是具体建造者。

产品:产品便是建造者中的复杂对象。一般来说一个系统会有多余一个的产品类,而这些产品类并不一定有共同的接口,而完全可以是不想关联的。


导演者与客户端打交道的,导演者将客户端创建产品的请求划分为对各个零件的建造请求,再将这些请求委派给具体建造者。具体建造者做具体建造工作,而客户端却不知道。


3、每一个产品类,就有一个相应的具体建造者类。


4、一个简单例子:只有一个产品,一个建造者


导演者:导演者有一个建造方法,负责调用具体建造者对象的零件方法,part1,part2等方法。


public class Director {


/**
* 我是导演者,负责调用具体建造者对象的零件建造方法
*/
private ConcreteBuilder builder;


// Builder builder;


public Director(Builder builder2) {
this.builder = (ConcreteBuilder) builder2;
}


/**
* 产品构造方法,负责调用各个零件建造方法
*/
public void construct() {
builder = new ConcreteBuilder();
System.out.println("开始生产产品");
builder.buildePart1();
builder.buildePart2();
builder.backResult();
}
}


抽象建造者与应用系统的商业逻辑无关。定义了建造方法返还方法。


import java.util.HashMap;
import java.util.Locale;
import java.util.ResourceBundle;


//抽象建造者,定义了具体的建造方法
abstract public class Builder {
// 产品零件建造方法
public abstract void buildePart1();


// 产品零件建造方法
public abstract void buildePart2();


// 产品返还方法
public abstract Product backResult();
}


具体建造者与应用系统的商业逻辑密切相关,总的来说这个角色应当将产品类实例化,并在各个建造方法中建造产品的各个零件,通过返还方法返回最终产品对对象。

产品类实例化


public class ConcreteBuilder extends Builder {


//产品类实例化
private Product product = new Product();


@Override
public void buildePart1() {
System.out.println("产品零件的第一部分");


}


@Override
public void buildePart2() {
System.out.println("产品零件的第二部分");


}


@Override
public Product backResult() {
System.out.println("完整产品");
return product;


}


}


产品类:与应用系统密切相关

public class Product {

}


客户端与导演者打交道的,导演者将客户端创建产品的请求划分为对各个零件的建造请求,再将这些请求委派给具体建造者。具体建造者做具体建造工作。


public class client {


private static Builder builder;
private static Director director;
public static void main(String[] args) {


builder =new ConcreteBuilder();

//director=new Director(builder);

director=new Director(builder);
director.construct();

System.out.println(director);
}


}


客户端负责创建导演者和具体建造者对象,然后客户把具体建造者对象交给导演者。导演者操纵具体建造者,开始建造产品,建造者把产品对象返还给客户端。
客户端虽然确实是具体建造者对象,但操纵具体建造者的任务却是属于导演者对象,把创建具体建造者对象的任务交给客户端而不是导演者,
是为了导演者对象与具体建造者对象的耦合变成动态的,从而使导演者对象可以操纵数个具体建造者对象中的任何一个。下面的例子就能更好的理解了。


结果输出


开始生产产品
产品零件的第一部分
产品零件的第二部分
完整产品
Director.Director@17fe89



5、下面是一个拥有两个产品的两个具体建造者的例子


抽象建造者定义了具体建造者的建造方法以及返还方法

//抽象建造者
abstract public class Builder {
// 产品零件建造方法
public abstract void buildePart1();


// 产品零件建造方法
public abstract void buildePart2();


// 产品返还方法
public abstract Product backResult();


// 用于生产电脑有参
// 生产cpu
public abstract void buildcpu(String cpu);


// 生产主板
public abstract void buildmainboard(String mainboard);


// 生产内存
public abstract void buildram(String ram);
}



一个抽象产品类,在产品返还的时候,返回的类型不应该是具体的某一个产品类型,实现产品接口后,就可以直接返还产品的类型了。


//两个产品的共同接口
public interface Product {


}
两个产品类实现产品接口



public class Product1 implements Product {


// 无参构造方法
public Product1() {
System.out.println("产品1");
}


}




//这个产品我们就用生活中的电脑为例
public class ProductComputer implements Product {


// 电脑包括这三个部分,就可以组装成电脑了
private String cpu;
private String mainboard;
private String ram;


// 有参构造方法
public ProductComputer(String cpu, String mainboard, String ram) {
super();
this.cpu = cpu;
this.mainboard = mainboard;
this.ram = ram;
}


public String getCpu() {
return cpu;
}


public void setCpu(String cpu) {
this.cpu = cpu;
}


public String getMainboard() {
return mainboard;
}


public void setMainboard(String mainboard) {
this.mainboard = mainboard;
}


public String getRam() {
return ram;
}


public void setRam(String ram) {
this.ram = ram;
}


// 无参构造方法
public ProductComputer() {
System.out.println("生产电脑产品");
}
}




产品1的具体建造者

//第一个产品的具体建造者
public class ConcreteBuilder1 extends Builder {


// 产品类实例化
private Product1 product = new Product1();


@Override
public void buildePart1() {
System.out.println("产品1零件的第一部分");


}


@Override
public void buildePart2() {
System.out.println("产品1零件的第二部分");


}


//向上转型,返还的都是Product,而不是具体的某个产品类型
@Override
public Product backResult() {
System.out.println("完整产品1");
return product;


}


@Override
public void buildcpu(String cpu) {
// TODO Auto-generated method stub


}


@Override
public void buildmainboard(String mainboard) {
// TODO Auto-generated method stub


}


@Override
public void buildram(String ram) {
// TODO Auto-generated method stub


}


}


产品2的具体建造者


public class ConcreteBuilder2 extends Builder {
// 电脑产品的具体建造者
// 产品类实例化
private ProductComputer product = new ProductComputer();


@Override
public void buildcpu(String cpu) {
System.out.println("生产电脑cpu");
product.setCpu(cpu);
}


@Override
public void buildmainboard(String mainboard) {
System.out.println("生产电脑主板");
product.setMainboard(mainboard);
}


@Override
public void buildram(String ram) {
System.out.println("生产电脑内存");
product.setRam(ram);
}


@Override
public void buildePart1() {
System.out.println("产品2零件的第一部分");


}


@Override
public void buildePart2() {
System.out.println("产品2零件的第二部分");


}


//向上转型,返还的都是Product,而不是具体的某个产品类型
@Override
public Product backResult() {
System.out.println("返还产品");
return product;


}


}


导演者角色



public class Director {


/**
* 我是导演者,负责调用具体建造者对象的零件建造方法
*/
private Builder builder;


// 构造方法


public Director(Builder builder) {
this.builder = builder;
}


/**
* 产品构造方法,负责调用各个零件建造方法
*/
public void construct() {
// builder = new Builder();
System.out.println("开始生产产品");
builder.buildePart1();
builder.buildePart2();
builder.backResult();
}


// 生产电脑的方法
// 这里返回的是Product,没有直接返回ProductComputer
public Product createComputer(String cpu, String mainboard, String ram) {


// 生产电脑控制流程
this.builder.buildmainboard(mainboard);
this.builder.buildcpu(cpu);
this.builder.buildram(ram);
return builder.backResult();
}
}


客户端

客户端负责创建导演者和具体建造者对象,然后客户把具体建造者对象交给导演者。导演者操纵具体建造者,开始建造产品,建造者把产品对象返还给客户端。
客户端虽然确实是具体建造者对象,但操纵具体建造者的任务却是属于导演者对象,把创建具体建造者对象的任务交给客户端而不是导演者,
是为了导演者对象与具体建造者对象的耦合变成动态的,从而使导演者对象可以操纵数个具体建造者对象中的任何一个。


public class client {


private static Builder builder;
private static Director director;


public static void main(String[] args) {


// 这里客户端选择实例化的具体建造者,调用非常方便。
// builder =new ConcreteBuilder1();
builder = new ConcreteBuilder2();


// director=new Director(builder);


// 把具体建造者对象交给导演者
director = new Director(builder);


// 导演者操纵具体建造者,开始建造产品
director.createComputer("i7", "华硕", "DDr4");


System.out.println(director);
}


}




生产电脑产品
生产电脑主板
生产电脑cpu
生产电脑内存
返还产品
doubleproduct.Director@b23210



产品1
开始生产产品
产品1零件的第一部分
产品1零件的第二部分
完整产品1
doubleproduct.Director@5973ea


6、通过两个实例,我们不难得出建造模式的UML图,通过UML图,我们就更加容易理解建造模式了。



通过此实例,相信对该模式有了进一步的认识。

每天努力一点,每天都在进步。






原创粉丝点击