「设计模式」建造者模式

109 阅读2分钟

一、概述

建造者模式,也叫生成器模式,可以理解成可以分步骤创建一个复杂的对象。在该模式中允许使用相同的创建代码生成不同类型和形式的对象。

结构模式

在建造者模式中,有 4 个定义:

①、Product(产品类) :我们具体需要生成的类对象

②、Builder(抽象建造者类):为我们需要生成的类对象,构建不同的模块属性,即:公开构建产品类的属性,隐藏产品类的其他功能。

③、ConcreteBuilder(具体建造者类):实现抽象类定义的所有方法,并返回一个组建好的对象。

④、Director(导演类):确定构建我们的类对象具体有哪些模块属性,在实际应用中可以不需要这个角色,直接通过client处理。

二、优缺点

  • 优点

(1)产品的建造和表示分离,实现了解耦,可以使用相同的创建过程得到不同的产品。

(2)将复杂产品的创建步骤分解在不同的方法中,使得创建过程更加清晰。

(3)增加新的具体建造者无需修改原有类库的代码,易于拓展,符合“开闭原则“。

  • 缺点

(1)产品必须有共同点,限制了使用范围。建造者模式创造出来的产品,其组成部分基本相同。

(2)产生多余的builder对象以及director对象,消耗内存。

三、实现方式

下面将结合我在开发中的建造者模式的使用案例(Datax)来了解一下该模式的实现方式。(在这里大家了不了解Datax不重要)在使用Datax的时候需要构建一个JSON配置文件,具体格式如下:

在构造这个JSON配置文件时,主要的需要组装readerwritersetting三个核心配置,最终组成一个完整的配置(产品)。

核心类解释

  • 抽象出一个产品 Product
  • 定义Builder接口,规定 Product 的构建步骤和过程。
  • ConcreteBuilder 实现类。
  • Director 统一构建过程。

Product

public class Product {
    private String reader;

    private String writer;

    private String setting;
}

Builder

public interface Builder {

    public void buildReader(String val);

    public void buildWriter(String val);

    public void buildSetting(String val);

    public Product getJson();
}

ConcreteBuilder

public class ConcreteBuilder implements Builder{

    Product dataJson = new Product();

    @Override
    public void buildReader(String val) {
        dataJson.setReader(val);
    }

    @Override
    public void buildWriter(String val) {
        dataJson.setWriter(val);
    }

    @Override
    public void buildSetting(String val) {
        dataJson.setSetting(val);
    }

    @Override
    public Product getJson() {
        return dataJson;
    }
}

Director

public class Director {

    //模拟 mysql -> hive
    public Product buildMysqlJson(Builder builder){
        builder.buildReader("mysql");
        builder.buildWriter("hive");
        builder.buildSetting("setting");
        return builder.getJson();
    }

    //模拟 oracle -> hive
    public Product buildOracleJson(Builder builder){
        builder.buildReader("oracle");
        builder.buildWriter("hive");
        builder.buildSetting("setting");
        return builder.getJson();
    }
}

Client

public class Client {
    public static void main(String[] args) {
        Director director = new Director();
        
        Product productMysql = director.buildMysqlJson(new ConcreteBuilder());
        System.out.println(productMysql.toString());

        Product productOracle = director.buildOracleJson(new ConcreteBuilder());
        System.out.println(productOracle.toString());
    }
}

输出>>

Product{reader='mysql', writer='hive', setting='setting'}
Product{reader='oracle', writer='hive', setting='setting'}

四、常见应用场景

在日常开发中我们能经常用到Builder设计模式,最常见的就是核心程序中的StringBuilder了,在开源框架中我们也经常能够看到,例如Mybatis中的SqlSourceBuilder、XMLConfigBuilder等信息。