Java二十三种设计模式-建造者模式(4/23)

建造者模式:构建复杂对象的专家

引言

建造者模式(Builder Pattern)是一种创建型设计模式,用于创建一个复杂的对象,同时允许用户只通过指定复杂对象的类型和内容就能构建它们,它将对象的构建和表示分离,使得相同的构建过程可以创建出不同的表示。

基础知识,java设计模式总体来说设计模式分为三大类:

(1)创建型模式,共5种:工厂方法模式、抽象工厂模式、单例模式、建造者模式、原型模式。

(2)结构型模式,共7种:适配器模式、装饰器模式、代理模式、外观模式、桥接模式、组合模式、享元模式。

(3)行为型模式,共11种:策略模式、模板方法模式、观察者模式、迭代子模式、责任链模式、命令模式、备忘录模式、状态模式、访问者模式、中介者模式、解释器模式。

第一部分:建造者模式概述

建造者模式是一种高级的创建型设计模式,旨在提供一种灵活的解决方案,用于创建复杂的对象。

1.1 定义与用途

建造者模式的基本定义

建造者模式将一个复杂对象的构建过程封装起来,同时允许按步骤构造对象。它允许用户通过相同的创建过程生成不同的表示。

为何在复杂对象的创建中需要建造者模式

  • 分离构建和表示:将对象的构建过程从其表示中分离出来,使得构建过程不会影响对象的使用。
  • 控制复杂性:对于包含多个组成部分的复杂对象,建造者模式可以逐步构建对象,而不是一次性完成,从而简化了构建过程。
  • 增强灵活性:允许系统在构建过程中的不同阶段进行修改,而不影响其他部分。

1.2 组成元素

产品(Product)

  • 定义:最终要创建的复杂对象。
  • 角色:通常是多个简单对象的组合体,由建造者模式逐步构建。

建造者(Builder)

  • 定义:一个接口,定义了创建产品的方法。
  • 角色:提供了一个抽象接口,使得不同的建造者可以构建同一产品的不同表示。

导演者(Director)

  • 定义:负责使用建造者来创建产品的类。
  • 角色:它知道如何使用建造者来得到最终的产品,通常持有一个建造者对象,并使用该对象的构建方法来创建产品。

具体建造者(Concrete Builder)

  • 定义:实现建造者接口的具体类。
  • 角色:实现具体的构建过程,通常包含一个产品对象,并定义了如何构建该产品的步骤。

客户端(Client)

  • 角色:使用导演者和建造者来获取最终的产品,客户端不直接与产品或具体建造者交互。

角色之间的交互

  • 客户端:通过导演者请求产品。
  • 导演者:使用具体建造者来构建产品。
  • 具体建造者:实现建造者接口,负责构建产品的具体步骤。

建造者模式特别适合于那些需要通过多个步骤来构建的对象,且这些步骤可能因不同的使用场景而异。通过使用建造者模式,我们可以在不牺牲对象的完整性和一致性的情况下,提供灵活的对象创建过程。在下一部分中,我们将通过Java代码示例来展示建造者模式的具体实现。

第二部分:建造者模式实现

2.1 Java实现示例

以下是使用Java语言实现建造者模式的一个示例。假设我们正在构建一个复杂的汽车对象,汽车由多个部件组成,如引擎、轮胎等。

// 产品接口
interface Car {void assembleEngine();void assembleWheels();// 其他组装方法...
}// 具体产品
class SportsCar implements Car {public void assembleEngine() {System.out.println("Assembling sports car engine.");}public void assembleWheels() {System.out.println("Assembling sports car wheels.");}// 其他组装方法实现...
}// 建造者接口
interface CarBuilder {CarBuilder setEngine();CarBuilder setWheels();// 其他设置方法...Car build();
}// 具体建造者
class SportsCarBuilder implements CarBuilder {private SportsCar car;public SportsCarBuilder() {this.car = new SportsCar();}public CarBuilder setEngine() {car.assembleEngine();return this;}public CarBuilder setWheels() {car.assembleWheels();return this;}// 其他设置方法...public Car build() {return car;}
}// 导演者
class CarDirector {public Car construct(CarBuilder builder) {return builder.setEngine().setWheels().build();}
}// 客户端代码
public class Client {public static void main(String[] args) {CarBuilder builder = new SportsCarBuilder();CarDirector director = new CarDirector();Car car = director.construct(builder);// 使用car...}
}

 

2.2 模式中的角色和职责

产品(Product)

  • 职责:定义最终要创建的复杂对象的接口。

建造者(Builder)

  • 职责:定义一个抽象接口,用于创建产品的不同部分。

导演者(Director)

  • 职责
    • 负责构建产品的步骤顺序。
    • 使用建造者接口来创建产品。

具体建造者(Concrete Builder)

  • 职责
    • 实现建造者接口,提供具体的构建步骤实现。
    • 存储产品的状态,并返回一个完整的产品。

客户端(Client)

  • 职责
    • 通过导演者使用建造者来获取最终的产品。
    • 客户端不直接与具体建造者交互,而是通过导演者和建造者接口。

相互作用

  • 客户端:请求导演者构建产品。
  • 导演者:通过调用具体建造者的方法,按照既定的顺序创建产品。
  • 具体建造者:实现具体的构建步骤,最终返回一个完整的产品。

建造者模式允许系统在创建复杂对象时保持灵活性和可扩展性。通过将构建过程封装在具体建造者中,导演者可以灵活地改变构建过程,而客户端则可以保持不变。在下一部分中,我们将探讨建造者模式的使用场景。

 

第三部分:建造者模式使用场景

3.1 复杂对象的构建

在软件开发中,有时我们需要构建的对象非常复杂,可能包含多个组件和配置选项。当对象的构建过程复杂时,建造者模式提供了一种清晰和灵活的方式来组织代码。

何时对象构建过程复杂:

  • 当对象的构造函数参数列表过长,难以管理时。
  • 当对象的创建需要多个步骤,且步骤之间存在条件逻辑时。

建造者模式的应用:

  • 通过将构建过程分解为一系列步骤,建造者模式简化了复杂对象的创建。
  • 它允许逐步设置对象的属性,而不是一次性在构造函数中完成。

3.2 对象的多样性

在某些情况下,我们需要构建的对象可能有多种变体,每种变体都有不同的属性和构建步骤。

建造者模式的优势:

  • 灵活性:可以轻松地添加或修改特定变体的构建步骤,而不影响其他变体。
  • 可维护性:通过将不同的构建步骤封装在不同的建造者中,提高了代码的可维护性。
  • 一致性:确保所有变体都通过相同的建造过程进行构建,保证了对象的一致性。

第四部分:建造者模式的优点与缺点

4.1 优点

灵活性

  • 建造者模式允许在构建过程中轻松地添加或修改步骤,从而创建不同的对象变体。

可扩展性

  • 当需要添加新的对象变体时,可以通过添加新的建造者来实现,而无需修改现有代码。

解耦

  • 客户端代码与对象的构建过程解耦,客户端不需要知道对象是如何构建的。

代码复用

  • 导演者可以使用相同的建造者来构建不同类型的产品,提高了代码的复用性。

4.2 缺点

系统复杂度

  • 引入建造者模式可能会增加系统的复杂度,特别是在建造者和产品类数量较多的情况下。

性能问题

  • 如果对象的构建过程非常简单,使用建造者模式可能会引入不必要的性能开销。

学习曲线

  • 对于新手来说,建造者模式可能比简单的构造函数或工厂方法更难理解。

建造者模式是一种强大的设计模式,适用于构建复杂且多变的对象。然而,它也需要谨慎使用,以避免不必要的复杂性和性能问题。在下一部分中,我们将比较建造者模式与其他设计模式,并提供一些最佳实践和建议。

第五部分:建造者模式与其他模式的比较

5.1 与工厂方法模式的比较

工厂方法模式

  • 定义:定义一个用于创建对象的接口,让子类决定实例化哪一个类。
  • 使用场景:当创建逻辑相对简单,且创建的对象种类较少时。

建造者模式

  • 定义:允许通过指定复杂对象的类型和内容来构建它们。
  • 使用场景:当创建的对象非常复杂,或者创建过程包含多个步骤时。

不同点

  • 复杂性:工厂方法模式适用于创建对象的逻辑相对简单的情况,而建造者模式适用于创建复杂对象。
  • 灵活性:建造者模式提供了更灵活的构建过程,允许逐步构建对象。

5.2 与抽象工厂模式的对比

抽象工厂模式

  • 定义:提供一个接口,用于创建一系列相关或相互依赖的对象。
  • 使用场景:当需要创建多个产品族,并且这些产品族之间存在依赖关系时。

建造者模式

  • 定义:允许用户通过指定复杂对象的类型和内容来构建它们。
  • 使用场景:当需要构建的对象具有多个组成部分,并且构建过程可能非常复杂时。

不同点

  • 产品族:抽象工厂模式关注于创建多个产品族,而建造者模式关注于构建单个复杂对象。
  • 依赖性:抽象工厂模式中的产品通常相互依赖,建造者模式则关注于单个对象的构建过程。

第六部分:最佳实践和建议

6.1 使用建造者模式的最佳时机

  • 复杂对象:当对象的构建涉及多个步骤或多个组成部分时。
  • 灵活性需求:当需要不同的构建过程来创建相同类型的对象时。

6.2 避免滥用建造者模式

  • 过度设计:避免在对象构建过程非常简单时使用建造者模式,这可能会导致不必要的复杂性。
  • 性能问题:在构建过程非常快速且不需要额外灵活性的情况下,使用建造者模式可能会引入不必要的性能开销。

6.3 替代方案

原型模式

  • 定义:通过复制现有的对象来创建新的实例。
  • 适用场景:当创建新对象的成本较高,或者需要快速复制现有对象时。

单例模式

  • 定义:确保一个类只有一个实例,并提供一个全局访问点。
  • 适用场景:当需要严格控制对象数量,确保全局只有一个实例时。

工厂方法模式

  • 适用场景:当创建对象的逻辑相对简单,且创建的对象种类较少时。

建造者模式是一种强大的设计模式,适用于构建复杂对象的场景。然而,合理选择使用时机和避免滥用同样重要。了解替代方案可以帮助开发者根据具体需求选择最合适的设计模式。

结语

建造者模式是处理复杂对象创建问题的有效工具。通过本文的深入分析,希望读者能够对建造者模式有更全面的理解,并在实际开发中做出合理的设计选择。

本文来自互联网用户投稿,该文观点仅代表作者本人,不代表本站立场。本站仅提供信息存储空间服务,不拥有所有权,不承担相关法律责任。如若转载,请注明出处:http://www.mzph.cn/news/871827.shtml

如若内容造成侵权/违法违规/事实不符,请联系多彩编程网进行投诉反馈email:809451989@qq.com,一经查实,立即删除!

相关文章

【机器学习】12.十大算法之一支持向量机(SVM - Support Vector Machine)算法原理讲解

【机器学习】12.十大算法之一支持向量机(SVM - Support Vector Machine)算法原理讲解 一摘要二个人简介三基本概念四支持向量与超平面4.1 超平面(Hyperplane)4.2 支持向量(Support Vectors)4.3 核技巧&…

【Django+Vue3 线上教育平台项目实战】构建课程详情页与集成视频播放功能

文章目录 前言一、课程列表页面a.后端代码b.前端代码 二、课程详情页面a. 视频播放功能的集成1.获取上传视频的链接地址2.集成在前端页面中1>使用vue-alipayer视频播放组件2>使用video标签 b. 页面主要内容展示1.后端代码1>分析表2>核心逻辑 2.前端代码3.效果图 前…

线程池-拒绝策略

线程池-拒绝策略 RejectedExecutionHandlerAbortPolicyCallerRunsPolicyDiscardPolicyDiscardOldestPolicy自定义拒绝策略 当核心线程已用尽 & 阻塞队列已满 & 超过最大线程数时,再向线程池提交任务,则会触发线程池的拒绝策略。 RejectedExecuti…

Python爬虫与文本到语音转换实战:获取并播报长沙天气

简介💕 在本文中,我们将通过一个简单的Python脚本,演示如何使用网络爬虫技术获取长沙的天气信息,并使用文本到语音技术将天气信息播报出来。我们将使用pyttsx3库进行语音播报,使用requests库来发起网络请求&#xff0…

自动驾驶-2D目标检测

yolo及yolo的变体 anchor boxes (锚框) intersection over union 并集交集 用于计算两个边界框的差异程度 bounding box predictions 边界框预测 non maximum suppression非极大值抑制 为了分离这些边界框并为每个对象获得单个边界框,我们使用IOU。这种获取单…

2024-07-15 Unity插件 Odin Inspector4 —— Collection Attributes

文章目录 1 说明2 集合相关特性2.1 DictionaryDrawerSettings2.2 ListDrawerSettings2.3 TableColumnWidth2.4 TableList2.5 TableMatrix 1 说明 ​ 本章介绍 Odin Inspector 插件中集合(Dictionary、List)相关特性的使用方法。 2 集合相关特性 2.1 D…

2-34 小波神经网络采用传统 BP 算法

小波神经网络采用传统 BP 算法,存在收敛速度慢和易陷入局部极小值两个突出弱点。建立了基于遗传算法的小波神经网络股票预测模型 GA-WNN。该模型结合了遗传算法的全局优化搜索能力以及小波神经网络良好的时频局部特性。运用 MATLAB 对拟合和预测过程进行仿真。结果表…

<数据集>绝缘子缺陷检测数据集<目标检测>

数据集格式:VOCYOLO格式 图片数量:2139张 标注数量(xml文件个数):2139 标注数量(txt文件个数):2139 标注类别数:8 标注类别名称:[insulator, broken disc, pollution-flashover, Two glass, Glassdirt…

李笑来思考框架的结晶《思考的真相》(2024 年新书)

点开文章的你肯定读过李笑来的书,比如讲认知的《财富自由之路》、讲管理自己的《把时间当做朋友》、讲财富底层逻辑的《财富的真相》、讲定投的《让时间陪你慢慢变富》等等。 李笑来的书不讲究华丽的文字,在意逻辑、论证的严谨,层层递进&…

数据结构之通过“ 队列 ”实现的“ 栈 ”功能。

🌹个人主页🌹:喜欢草莓熊的bear 🌹专栏🌹:数据结构 前言 本节内容是利用“ 队列 ”先进先出的特点 实现 “ 栈 ” 先进后出。 一、题目 1.1 题目描述: 请你仅使用两个队列实现一个后入先出&…

成为CMake砖家(1): 在Windows上查看CMake文档

大家好,我是白鱼。 在使用 CMake 的过程中,想必有不少朋友像我一样, 想在本地查看 CMake 文档。 首先安装 CMake, Installer 版本: 安装后,从开始菜单输入 CMake, 选择结果中的 “CMake Documentation”…

如何在 Shell 脚本中使用函数 ?

函数是一个可重用的代码块。我们经常把重复的代码放入一个函数中,并从不同的地方调用该函数,库是函数的集合。我们可以在库中定义常用的函数,其他脚本可以使用它们而无需复制代码。 Calling function 在 Shell 中,调用函数和调用…

1.33、激活可视化卷积神经网络(matalb)

1、激活可视化卷积神经网络原理及流程 激活可视化(Activation Visualization)指的是通过可视化神经网络中激活函数的输出,来理解神经网络是如何学习并提取特征的过程。在卷积神经网络(CNN)中,我们可以通过…

tomcat的优化、动静分离

tomcat的优化 tomcat自身的优化 tomcat的并发处理能力不强,大项目不适应tomcat做为转发动态的中间件(k8s集群,pytnon rubby),小项目会使用(内部使用的)动静分离 默认配置不适合生产环境&…

MySQl高级篇 -索引优化篇

索引 InnoDB采用了一个B数来存储索引,使得在千万级数据量的一个情况下,树的高度可以控制在3层以内,而层高代表磁盘IO的一个次数,因此基于索引查找可以减少磁盘IO的次数 MySQL的索引是在存储引擎层实现的,不同的存储引…

头歌资源库(31)象棋中马遍历棋盘的问题

一、 问题描述 二、算法思想 这是一个典型的深度优先搜索问题。 首先,我们创建一个mn的棋盘,并初始化所有的点为未访问状态。 然后,我们从(0, 0)位置开始进行深度优先搜索。 在每一步中,我们先标记当前位置为已访问&#xff0…

Android Viewpager2 remove fragmen不生效解决方案

一、介绍 在如今的开发过程只,内容变化已多单一的fragment,变成连续的,特别是以短视频或者直播为主的场景很多。从早起的Viewpage只能横向滑动,到如今的viewpage2可以支持横向或者竖向滑动。由于viewpage2的adapter在设计时支持缓…

解决mysql,Navicat for MySQL,IntelliJ IDEA之间中文乱码

使用软件版本 jdk-8u171-windows-x64 ideaIU-2021.1.3 mysql-essential-5.0.87-win32 navicat8_mysql_cs 这个问题我调试了好久,网上的方法基本上都试过了,终于是解决了。 三个地方结果都不一样。 方法一 首先大家可以尝试下面这种方法&#xff1a…

基于Python+Django+MySQL+Echarts的租房数据可视化分析系统

租房数据可视化 DjangoMySQLEcharts 基于PythonDjangoMySQLEcharts的租房数据可视化分析系统 Echarts 信息存储在数据库中 不含爬虫代码,或爬虫代码已失效 不支持登录注册 简介 基于DjangoMySQLEcharts的租房数据可视化系统通过连接数据库获取数据&#xff0c…

【格密码基础】旋转格的性质

目录 一. 回顾ZSVP问题 二. 基于ZSVP问题的密码系统 三. 格基旋转与Gram矩阵 四. 补充矩阵QR分解 4.1 矩阵分解 4.2 举例 前序文章请参考: 【格密码基础】详解ZSVP问题-CSDN博客 一. 回顾ZSVP问题 根据之前的讨论我们知道解决ZSVP问题的计算复杂度为&#x…