今天学习了建造者模式
它的定义是这样的:将一个复杂对象的构建与它的表示分离,使得同样的构建过程可以创建不同的表示
建造者模式中,有如下四种角色
1:Product产品类 通常实现的是模板方法和基本方法
2:Builder抽象建造者,规范产品的组件,一般是由子类实现
3:ConcreteBuilder 是先抽象类定义的所有方法,并且返回一个组建好的对象
4:Director导演类 负责安排一有模板的顺序,然后告诉Builder开始建造
假设有这样一种情况。我现在想要创建各种不同的动物,我已经归纳出了所有动物可能存在的活动:吃,跑,爬,叫,跳五种
我想能创建各种不同的动物他们可以组合各种活动。比如羊:吃,跑,叫;乌龟:吃,爬;等等等,或者还要规定这些动物的活动顺序等。
如果不适用建造者模式,那么情况就会变得非常复杂,因为你每多一种动物,就要多写一个实现类,而需求的变化是无限的,所以想到适用建造者模式。
Product产品类
package com.gengu.建造模式;
import java.util.ArrayList;
import java.util.List;
/**
* 动物的抽象模板
* 定义了很多动物所公有的特性
* */
public class Animal {
/**定义这个动物的活动顺序*/
List<String> list = new ArrayList<String>();
//跑
public void run(){
System.out.println("running");
}
//叫
public void cry(){
System.out.println("crying");
}
//吃
public void eat(){
System.out.println("eating");
}
//爬
public void crawl(){
System.out.println("crawling");
}
//跳
public void jump(){
System.out.println("jumping");
}
//执行方法
public void execute(){
for(String str:list){
if(str.equalsIgnoreCase("run")){
this.run();
}else if(str.equalsIgnoreCase("eat")){
this.eat();
}else if(str.equalsIgnoreCase("crawl")){
this.crawl();
}else if(str.equalsIgnoreCase("jump")){
this.jump();
}else if(str.equalsIgnoreCase("cry")){
this.cry();
}
}
}
}
Builder抽象建造者
package com.gengu.建造模式;
import java.util.List;
/**由它来构建各种动物 要什么样的动物都由相关的子类完成*/
public abstract class AnimalBuilder {
//构建各种动物的活动组合
public abstract void setList(List<String> list);
//返回我们创建的动物
public abstract Animal getAnimal();
}
动物的实现类
package com.gengu.建造模式;
import java.util.List;
public class ConcreteAnimal extends AnimalBuilder{
//定义一个私有变量
private Animal animal = new Animal();
@Override
public Animal getAnimal() {
return this.animal;
}
@Override
public void setList(List<String> list) {
this.animal.list = list;
}
}
导演类,规定了羊怎么创建,乌龟怎么创建
package com.gengu.建造模式;
import java.util.ArrayList;
import java.util.List;
/**导演类*/
public class Director {
List<String> list = new ArrayList<String>();
AnimalBuilder animalBuilder = new ConcreteAnimal();
/**
* 得到羊
* 那么就有:跑,叫,吃的活动
* */
public Animal getSheep(){
list.clear();
list.add("run");
list.add("eat");
list.add("cry");
this.animalBuilder.setList(list);
return this.animalBuilder.getAnimal();
}
/**
* 得到乌龟
* 那么就有:吃,爬的活动
* */
public Animal getTortoise(){
list.clear();
list.add("crawl");
list.add("eat");
this.animalBuilder.setList(list);
return this.animalBuilder.getAnimal();
}
}
测试类
package com.gengu.建造模式;
public class Client {
public static void main(String[] args) {
Director director = new Director();
Animal sheep = director.getSheep();
System.out.println("羊的活动有以下几种");
sheep.execute();
System.out.println("================");
Animal tortoise = director.getTortoise();
System.out.println("乌龟的活动有以下几种");
tortoise.execute();
}
}
这样的话,如果我需要再扩展一个鸵鸟,那么只需要在导演类里面添加一个得到鸵鸟的方法,扩展性非常好。它将创建产品的细节放到了导演类中,这样具有很好的安全性,因为各个动物的创建过程是独立的,不对其他任何模块产生影响。