当前位置: 首页 > news >正文

Java设计模式之<建造者模式>

目录

1、建造者模式

2、建造者模式结构

3、实现

4、工厂模式对比

5、适用场景差异


前言

        建造者模式是一种创建型设计模式。用于封装复杂对象的构建过程,通过步骤构建产品类。它包括产品类、抽象建造者具体建造者指挥者角色

        优点在于灵活性、解耦和易扩展,缺点是增加工作量和效率较低。适用场景如构建套餐、字符串动态构建、StreamAPI操作等。


1、建造者模式

(Builder Pattern)建造者模式定义:封装一个复杂对象构造过程,并允许按步骤构造。

        将一个复杂对象的构建(如何分步组装)和其表示(最后生成的产品)分离。使同样的构建过程可以创建不同表现(参数组合)的对象。

  • 针对复杂对象,构建流程有“步骤”,可以按需改变每一步内容或顺序
  • 最终可以生成不同个性化的产物(同样流程,不同参数或细节)


2、建造者模式结构

如下所示:

  1. Product(产品类):最终要建造的复杂对象。
  2. Builder(抽象建造者):定义构建产品各部分的接口。
  3. ConcreteBuilder(具体建造者):实现 Builder 接口,每步怎么造。
  4. Director(指挥者):决定调用哪些步骤,以及什么顺序,控制“组装流程”。

3、实现

假设建造一个定制汉堡(面包、肉、蔬菜、酱料等均可变),可以有不同套餐。

1. 产品类

class Burger {private String bread;private String meat;private String vegetable;private String sauce;// setter/getter略@Overridepublic String toString() {return "Burger{" +"bread='" + bread + '\'' +", meat='" + meat + '\'' +", vegetable='" + vegetable + '\'' +", sauce='" + sauce + '\'' +'}';}
}

2. 抽象建造者

interface BurgerBuilder {BurgerBuilder chooseBread(String bread);BurgerBuilder chooseMeat(String meat);BurgerBuilder chooseVegetable(String vegetable);BurgerBuilder chooseSauce(String sauce);Burger build();
}

3. 具体建造者

class DefaultBurgerBuilder implements BurgerBuilder {private Burger burger = new Burger();@Overridepublic BurgerBuilder chooseBread(String bread) {burger.setBread(bread);return this;}@Overridepublic BurgerBuilder chooseMeat(String meat) {burger.setMeat(meat);return this;}@Overridepublic BurgerBuilder chooseVegetable(String vegetable) {burger.setVegetable(vegetable);return this;}@Overridepublic BurgerBuilder chooseSauce(String sauce) {burger.setSauce(sauce);return this;}@Overridepublic Burger build() {return burger;}
}

4. 指挥者 Director(可选)

如果产品组合很复杂,可以有个指挥者预设“套餐”:

class BurgerDirector {public Burger createCheeseBeefBurger(BurgerBuilder builder) {return builder.chooseBread("芝麻面包").chooseMeat("牛肉").chooseVegetable("生菜").chooseSauce("芝士酱").build();}// 也可有 createSpicyChickenBurger() ...
}

5. 客户端使用

public class TestBuilder {public static void main(String[] args) {BurgerBuilder builder = new DefaultBurgerBuilder();// 自定义装配Burger burger = builder.chooseBread("全麦").chooseMeat("鸡肉").chooseVegetable("番茄").chooseSauce("千岛酱").build();System.out.println(burger);// 使用预定义指挥者装配套餐BurgerDirector director = new BurgerDirector();Burger cheeseBurger = director.createCheeseBeefBurger(new DefaultBurgerBuilder());System.out.println(cheeseBurger);}
}

结果输出:

Burger{bread='全麦', meat='鸡肉', vegetable='番茄', sauce='千岛酱'}
Burger{bread='芝麻面包', meat='牛肉', vegetable='生菜', sauce='芝士酱'}

4、工厂模式对比

特点:

  • 创建对象时,一次性指定参数,直接new或工厂create返回对象
  • 不能灵活分步骤定制产物,组合变化很局限
  • 适合产品结构简单、参数少、变化小的“快速生产”

简单工厂/工厂方法代码:

// 简单工厂
class BurgerFactory {public static Burger createCheeseBurger() {Burger b = new Burger();b.setBread("芝麻面包");b.setMeat("牛肉");b.setVegetable("生菜");b.setSauce("芝士酱");return b;}public static Burger createChickenBurger() { ... }
}// 使用
Burger burger = BurgerFactory.createCheeseBurger();

对比:

  • 工厂模式:侧重产物种类,比如“要A还是B”,流程和细节厂内规定死了,客户端改不了。
  • 建造者模式:侧重“每一步都能自由定制和变化”,组装细节自己掌握,可以一个build流程装不同产品,还能链式调用、流式风格。

5、适用场景差异

如下所示:

 

1、Lombok的@Builder注解

支持链式建造大对象。

2、StringBuilder/StringBuffer

3、MyBatis的SqlSessionFactoryBuilder

4、复杂业务DTO装配,配置文件装配器

5、Stream API:

将集合类转为stream流,通过一系列的中间操作和终止操作来生成最终结果。


总结

1、建造者模式适用于:

复杂对象的*组装、参数变化多、“按步构建”*的场景,强调流程可扩展、定制化强

2、工厂模式适用于:

产品类目变化,强调“要什么生产什么”,但组装流程是固定的、透明的


参考文章:

1、设计模式第10讲——建造者模式(Builder)-CSDN博客文章浏览阅读1.9w次,点赞68次,收藏204次。建造者模式是一种创建型设计模式,用于封装复杂对象的构建过程,通过步骤构建产品类。它包括产品类、抽象建造者、具体建造者和指挥者角色。优点在于灵活性、解耦和易扩展,缺点是增加工作量和效率较低。适用场景如构建套餐、字符串动态构建、StreamAPI操作等。代码示例展示了如何用建造者模式构建肯德基套餐。 https://blog.csdn.net/weixin_45433817/article/details/131175862?ops_request_misc=%257B%2522request%255Fid%2522%253A%2522a704756060a8db0d2183b3418eedf674%2522%252C%2522scm%2522%253A%252220140713.130102334..%2522%257D&request_id=a704756060a8db0d2183b3418eedf674&biz_id=0&utm_medium=distribute.pc_search_result.none-task-blog-2~all~top_positive~default-1-131175862-null-null.142^v102^control&utm_term=%E5%BB%BA%E9%80%A0%E8%80%85%E6%A8%A1%E5%BC%8F&spm=1018.2226.3001.4187

http://www.lryc.cn/news/602321.html

相关文章:

  • idea编译报错 java: 非法字符: ‘\ufeff‘ 解决方案
  • 解决windows系统下 idea、CLion 控制台中文乱码问题
  • 机器学习sklearn:不纯度与决策树构建
  • Rust实战:AI与机器学习自动炒饭机器学习
  • Linux系统Centos7 安装mysql5.7教程 和mysql的简单指令
  • 搭建HAProxy高可用负载均衡系统
  • 【拓扑排序 缩点】P2272 [ZJOI2007] 最大半连通子图|省选-
  • Linux应用开发基础知识——LInux学习FreeType编程(七)
  • 【C++进阶】---- 二叉搜索树
  • 基于LangGraph Cli的智能数据分析助手
  • Android中PID与UID的区别和联系(2)
  • Go 语言面试题
  • 数据分析干货| 衡石科技可视化创作之仪表盘控件如何设置
  • GitLab 公共仓库:coding 用到的 git 命令
  • Springboot社区养老保险系统小程序
  • 一文理清 Linux 软件管理核心知识:从程序组成到包管理工具
  • Java面试宝典:MySQL8新特性
  • shell学习从入门到精通(第二部分)
  • 机器学习sklearn:决策树的参数、属性、接口
  • nccl中__syncthreads的作用及例子 (来自deepseek)
  • 135端口与WMI攻防全解析
  • 网络安全基础知识【4】
  • python中类变量 __slots__ 解析
  • 5190 - 提高:DFS序和欧拉序:树上操作(区域修改1)
  • 排序算法 (Sorting Algorithms)-JS示例
  • AI原生应用:从人机关系重构到数字空间革命
  • RF随机森林分类预测+特征贡献SHAP分析,通过特征贡献分析增强模型透明度,Matlab代码实现,引入SHAP方法打破黑箱限制,提供全局及局部双重解释视角
  • 力扣7:整数反转
  • OCR 赋能合同抽取:不良资产管理公司的效率加速器
  • Kafka 顺序消费实现与优化策略