聚沙成塔:聊聊建造者模式

欢迎关注微信公众号:互联网全栈架构

建造者(Builder)模式属于创建型设计模式,它的定义如下:

f204527a85848e6b645d80e5a54c3a25.png

将一个复杂对象的创建与它的表示分离,使得同样的创建过程可以产生不同的表示。这样的定义可能略微有点佶屈聱牙,简单来讲,建造者模式可以让你使用同样的步骤创建出不同属性的复杂对象。

建造者模式主要包括以下几个角色:

抽象建造者(Builder):它声明了通用的产品创建步骤。

具体建造者(Concrete Builder):实现了Builder接口,完成产品各个部分的创建工作。

产品(Product):最终要创建的复杂对象。

指挥者(Director):控制产品创建过程,定义产品创建的执行顺序。

5982e3c9ac310b619c6f7da803f1303f.png

建造者模式UML类图

我们以建造房屋为例来进行说明,不论修建什么类型的房屋,都会经历打地基、铺地板、砌墙壁、盖屋顶这么几个步骤,但房屋类型不同,每一步的具体做法可能会有差别,比如盖一栋别墅,地基可能不需要打得那么深,但对于高层居民楼,地基就需要挖得深一些了。当然,这只是为了举例说明建造者模式的含义,实际生活中的房屋建造肯定复杂得多。

首先定义产品类,房屋具有地基、地板、墙壁和屋顶等属性:

package com.sample.patterns.builder;
// 房屋,具有地基、地板等属性
public class House {
    private String foundation;
    private String floor;
    private String wall;
    private String roof;
    // 省略getter和setter
}

接下来是抽象建造者,它定义了建造房屋所需要的步骤(不是顺序):

package com.sample.patterns.builder;
// 抽象建造者,定义了产品创建的步骤
public interface HouseBuilder {
    void buildFoundation();
    void buildRoof();
    void buildWall();
    void buildFloor();
    House getResult();
}

然后是具体的建造者,一个是别墅,一个是普通房屋:

package com.sample.patterns.builder;
// 别墅的修建方法
public class VillaHouseBuilder implements HouseBuilder{
    private House house = new House();
    @Override
    public void buildFoundation() {
        System.out.println("打造别墅的地基");
    }
    @Override
    public void buildRoof() {
        System.out.println("修建别墅的屋顶");
    }
    @Override
    public void buildWall() {
        System.out.println("修建别墅的墙壁");
    }
    @Override
    public void buildFloor() {
        System.out.println("铺设别墅的地板");
    }
    @Override
    public House getResult() {
        return house;
    }
}

普通房屋的builder类跟别墅的builder类很相似,只是每个方法的实现内容不一样,此处不再贴出代码。

指挥者角色控制了房屋修建的过程,也就是各个步骤的调用顺序:

package com.sample.patterns.builder;
// 房屋建造的指挥者
public class HouseDirector {
    public House construct(HouseBuilder houseBuilder){
        houseBuilder.buildFoundation();
        houseBuilder.buildFloor();
        houseBuilder.buildWall();
        houseBuilder.buildRoof();
        return houseBuilder.getResult();
    }
}

最后,客户端使用建造者模式来修改一栋房屋,它或者是一栋别墅,或者是一栋普通房屋:

package com.sample.patterns.builder;
// 客户端
public class Client {
    public static void main(String[] args) {
        HouseDirector houseDirector = new HouseDirector();
        
        HouseBuilder villaBuilder = new VillaHouseBuilder();
        House villa = houseDirector.construct(villaBuilder);

        HouseBuilder commonBuilder = new CommonHouseBuilder();
        House common = houseDirector.construct(commonBuilder);
    }
}

在上面的示例中,我们通过房屋的修建过程来演示了建造者模式的使用方法,抽象建造者规定了创建产品所需要经历的步骤,而每一步的实现方法则由具体建造者来执行;指挥者角色规定了这些步骤的顺序,并返回产品对象,如果我们需要其它不同类型的房屋,我们直接新增一个具体建造者即可,而不用改变房屋对象本身,这就是将对象的创建过程与表示进行了分离。

建造者模式的应用比较广泛,在JDK源码,或者Spring框架源码中,经常可以看到它的身影,比如StringBuilder类,BeanDefinitionBuilder等。在实际编码过程中,如果我们定义一个类,构造函数的参数很复杂,可以考虑使用建造者模式进行改造。

都看到这里了,请帮忙一键三连啊,也就是点击文末的在看、点赞、分享,这样会让我的文章让更多人看到,也会大大地激励我进行更多的输出,谢谢!

鸣谢:

https://refactoring.guru/design-patterns/builder

推荐阅读:

公司裁员,码农竟然成了“帮凶”?(剧情杜撰)

删除重复记录但保留其中一行数据的sql写法

一条sql搞定这个需求,面试官直呼内行

MySQL如何进行表之间的关联更新

高频面试题:多线程顺序打印ABC字符20次

一网打尽:MySQL索引失效的场景大搜罗

这个设计模式的用法,一般人我不告诉他

评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值