设计模式:创建型模式:建造者模式

199 阅读4分钟

引言

  1. 生产和组装汽车需要的工序是:生产发动机、生产汽车外壳、将发动机组装到外壳中、生产轮胎、将轮胎组装到汽车外壳中。
  2. 生产汽车的过程虽然都是一样的,但是不同配置的汽车对每个零件的等级也是不同的。

建造者模式概述

  1. 也叫生成器模式,是一种用于构建对象的模式。它可以将复杂对象的构建步骤抽象出来成为一个抽象类或者接口,使这几个抽象的方法由不同实现类来实现方法,这样可以构造出不同表现(具有不同属性)的子类对象。
  2. 建造者模式是一步一步创建一个复杂的对象,它允许用户只通过指定复杂对象的类型和内容就可以构建它们,用户不需要知道内部的具体构建细节是怎么实现的。

包含的具体角色

  1. Product(产品角色):一个具体的产品对象。
  2. Builder(抽象建造者):一个可以创建Product对象的各个零件的接口或者抽象类,包含创建多个部件的方法列表。
  3. ConcreteBuilder(具体建造者):Builder的实现类或者子类,用于具体细节地去创建Product对象的各个零件, 实现每一个 零件 创建的方法的具体类。
  4. Director(指挥者):内部会构建一个Builder实现类或者子类的对象,用于创建一个复杂的对象;作用其一是将用户与产品生产过程进行了隔离,其二是可以控制产品的生产过程

代码

/**

  • 汽车

  • @author Peter */ public class Car {

    /**

    • 汽车外壳 / private CarShell carShell; /*
    • 汽车发动机 */ private Engine engine;

    /**

    • 汽车轮胎 */ private Tyre tyre; }
/**
 * 抽象汽车建造者接口
 * @author Peter
 */
public  interface CarBuilder {

    // 建造 汽车外壳
    CarShell  buildCarShell();
    
    // 建造 引擎
    Engine  buildEngine();
    
    // 建造轮胎
    Tyre  buildTyre();
}

/**
 * 标配汽车建造者, 具体建造者,封装每一个零件的建造过程
 * @author Peter
 */
public class StandardCarBuilder implements CarBuilder{
    
    /**
     * 建造汽车外壳
     * @return
     */
    @Override
    public  CarShell  buildCarShell(){
        return new CarShell("标配汽车外壳");
    }
    
    /**
     * 建造发动机
     * @return
     */
    @Override
    public  Engine  buildEngine(){
        return new Engine("标配汽车发动机");
    }
    
    /**
     * 建造轮胎
     * @return
     */
    @Override
    public  Tyre  buildTyre(){
        return new Tyre("标配汽车轮胎");
    }
}

/**
 * 汽车建造指挥者, 控制建造顺序
 * @author Peter
 */
public class CarDirector {

    private CarBuilder carBuilder = null;
    
     
	public CarDirector() {
	}

	//构造器注入
    public CarDirector(CarBuilder carBuilder) {
        this.carBuilder = carBuilder;
    }

    //set方法注入
    public void setCarBuilder(CarBuilder carBuilder) {
        this.carBuilder = carBuilder;
    }

    /**
     * 将汽车的组装过程交给指挥者来控制
     * @return
     */
    public Car buildCar() {
        
    	Engine engine = carBuilder.buildEngine();
        CarShell carShell = carBuilder.buildCarShell();
        System.out.println("将"+engine+"组装到"+carShell+"中");
        Tyre tyre = carBuilder.buildTyre();
        System.out.println("将"+tyre+"组装到"+carShell+"中");
        
        Car car=new Car();
        car.setEngine(engine);
        car.setCarShell(carShell);
        car.setTyre(tyre);
        return car;
    }
}

使用总结

  1. 建造者模式是用于创建复杂的对象且这个复杂的对象的加工有一定顺序要求的。
  2. 也就是说这个对象的创建是由多个零件组成的且在创建过程中组装每个零件的都是有步骤要求的。
  3. 可以更加精细地去控制产品的创建过程,将复杂产品的创建步骤分解在不同的方法中,使得创建过程更加清晰,也更方便在代码中去控制创建过程,具有很好的可读性。
  4. 增加具体的建造者无需修改原有的产品类代码,指挥者类是面向抽象的建造者编程,所以具有很好的可扩展性,遵守了开闭原则和依赖倒置原则。

建造者模式和工厂模式的区别

  1. 工厂模式注重的是整体对象的创建方法,而建造者模式注重的最终的那个复杂对象的创建过程,创建对象的过程方法可以在创建时自由调用。使用工厂模式是不关心产品的构建过程的,只关心什么类型的产品由什么类型的工厂去创建,而建造者模式是要求按照指定的工序去建造产品,它的主要目的是通过组装不同的零件而产生一个新的产品。

复杂对象

  1. 复杂对象:内部持有的属性都是很多自定义引用的类型。
  2. 简单对象:内部的属性都是基本类型和String 类型的。

JDK以及典型框架中 建造者模式的应用

  1. StringBuilder
    • 抽象builder类:
public interface Appendable {
        Appendable append(CharSequence csq) throws IOException;
} 
  • 具体建造者类, 实现了append方法
abstract class AbstractStringBuilder implements Appendable {
    public AbstractStringBuilder append(String str) {
        if (str == null)
            return appendNull();
        int len = str.length();
        ensureCapacityInternal(count + len);
        str.getChars(0, len, value, count);
        count += len;
        return this;
    }
}
  • 指挥者 StringBuilder: 调配了父类的 append方法,构建顺序。
  1. Mybatis 中 SqlSessionFactoryBuilder 也使用了建造者模式
  2. Spring 中的 BeanDefinetionBudiler