建造者设计模式6

一、定义

        官方定义:将一个复杂对象的构建和表示分离,使同样的构建过程可以创建不同的表示。

        官方定义真的是....,好吧,让我来指点迷津。

二、建造者需要的几个角色

        1.Product产品类。这个产品类比较复杂,内部有许多其它类的对象的引用,可以视为此产品类的逻辑上必不可少的“组成部分”。当我们要构造出此产品的时候,产品持有的其它引用也必须得到初始化。

        2.Builder建造者。这是一个抽象接口,用于定义生产产品的各个“组成部分”。

        3.ConcreteBuilder建造者实现类。具体生产出产品对象的各个组成部分。

        4.Director指挥者。调用建造者实现类来生产出产品的各个组成部分,并将其装配到产品类中。

三、建造模式心法

        

        建造模式与工厂模式十分相似。

        区别在于:

        工厂模式关心的是“生产出来的产品”,对于其构造过程的顺序不关心。

        建造者设计模式强调的是构造顺序,它对于产品的构造过程有着合理的顺序控制,这好比Spring有顺序的注入合作者Bean一样。不同的构造顺序,可能生产出不同的产品。

        现在可以解释官方的定义:将一个复杂对象的构建(产品复杂的构造过程)和表示(用户拿到的产品对象的地方,或者说是能够进行调用产品对象的环境)分离,使同样的构建过程(抽象建造者定义的统一接口,Builder类的意思)可以创建不同的表示(不同的具体建造者,产生不同的产品)。简单说:让调用环境与产品复杂的构造逻辑解耦。

        现在的效果就是,在客户端拿到的产品,它是怎么创建的,我们不知道。如果我们想手动创建产品,那么将会出现下面的代码:先Product product = new Product();  product.setA();product.setB();......product.setL();这样代码又多又长。更加糟糕的是,如果需求变了,使用到product的地方都要修改set方法,难怪要加班啊。欲哭无泪。

        如果是Product product = Director.getProduct(具体建造者类);即使需求变了,只需要修改具体建造者类的代码。因此,在我们的调用环境中,避免了与产品的复杂构造逻辑耦合,是建造者模式的一大好处。

四、例子

        

        推荐一个无法超越的经典例子:建造者模式,作者:汉森X

        下面的例子是我自己写的,很烂,推荐看推荐的经典例子。

public class Person {
    private String Coat;//外套

    private String jeans;//牛仔裤

    private String shoes;//鞋子

    public Person() {
    }

    public void setCoat(String coat) {
        Coat = coat;
    }

    public void setJeans(String jeans) {
        this.jeans = jeans;
    }

    public void setShoes(String shoes) {
        this.shoes = shoes;
    }

    @Override
    public String toString() {
        return "Person{" +
                "Coat='" + Coat + '\'' +
                ", jeans='" + jeans + '\'' +
                ", shoes='" + shoes + '\'' +
                '}';
    }
}

//建造者接口Builder,可以视为抽象的衣橱,提供衣服
interface Builder{
    String provideCoat();

    String provideJeans();

    String provideShoes();
}

//构造者实现类。可以视为具体衣橱,比如自己家里面的衣橱
class ConcreteBuilder implements Builder{
    @Override
    public String provideCoat() {
        return "霸气外套";
    }

    @Override
    public String provideJeans() {
        return "七匹狼牛仔裤";
    }

    @Override
    public String provideShoes() {
        return "耐克鞋子";
    }
}

class Director{
    private Builder builder;

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

    public Person getPerson(){
        Person person = new Person();
        person.setCoat(builder.provideCoat());
        person.setJeans(builder.provideJeans());
        person.setShoes(builder.provideShoes());
        return person;
    }
    //主函数视为调用环境,比如Controller中,或者是Service中
    public static void main(String[] args) {
        Builder builder = new ConcreteBuilder();
        Director director = new Director(builder);
        Person person = director.getPerson();
        System.out.println(person);//Person{Coat='霸气外套', jeans='七匹狼牛仔裤', shoes='耐克鞋子'}
    }
}

五、优缺点

        

        优点:

        1.建造者模式有效的隐藏了类的构造过程,这个过程转由专门的类来提供实现,避免在客户端环境中与产品类复杂的构造逻辑耦合。

        2.建造者模式是将产品复杂的构造过程封装在内部,对于外部调用的人来说,只需要传入建造者Director和建造工具ConcreteBuilder,对于内部是如何建造成成品的,调用者无需关心。

        3.具体的建造者类逻辑独立,既可以创建新的建造者,又能在修改特定建造者类的同时,不影响其它建造者类,符合开放闭合原则。

        缺点:

        类比较多,代码开发量变大。解决方案是,我们可以在具体的建造者类中加入返回产品的方法,这就意味着,Director类将被删除,它的“按顺序装配产品与返回具体产品”的两个功能直接由具体建造者来提供。

分割线--------------------------------------------------------------------------------------------

下一篇:原型设计模式7

 

猜你喜欢

转载自blog.csdn.net/yanluandai1985/article/details/79866876