【设计模式】创建型设计模式之 建造者模式

文章目录

  • 一、介绍
      • 定义
      • UML 类图
  • 二、用法1 简化复杂对象具体构建过程
      • 省略抽象的 Builder 类
      • 省略 Director 类
  • 三、用法2 控制对象构造方法、限制参数关系
      • Guava 中使用建造者模式构建 cache 来进行参数校验

一、介绍

定义

建造者模式,将一个复杂的对象的构建过程与表示分离,使得同样的构建过程可以构建不同的结果。

UML 类图

  1. 抽象建造者类(Builder):这个接口规定要实现复杂对象的哪些部分的创建,并不涉及具体的部件对象的创建。
  2. 具体建造者类(ConcreteBuilder):实现 Builder 接口,完成复杂产品的各个部件的具体创建方法。在构造过程完成后,提供一个方法,返回创建好的负责产品对象。
  3. 产品类(Product):要创建的复杂对象 (包含多个组成部件).
  4. 指挥者类(Director):调用具体建造者来创建复杂对象的各个部分,在指导者中不涉及具体产品的信息,只负责保证对象各部分完整创建或按某种顺序创建(客户端一般只需要与指挥者进行交互)。

二、用法1 简化复杂对象具体构建过程

public class Bike {//车架private String frame;//座椅private String seat;public String getFrame() {return frame;}public void setFrame(String frame) {this.frame = frame;}public String getSeat() {return seat;}public void setSeat(String seat) {this.seat = seat;}
}
public abstract class Builder {protected Bike mBike = new Bike();public abstract void buildFrame();public abstract void buildSeat();public abstract Bike createBike();
}public class HelloBuilder extends Builder {@Overridepublic void buildFrame() {mBike.setFrame("碳纤维车架");}@Overridepublic void buildSeat() {mBike.setSeat("橡胶车座");}@Overridepublic Bike createBike() {return mBike;}
}public class MobikeBuilder extends Builder {@Overridepublic void buildFrame() {mBike.setFrame("铝合金车架");}@Overridepublic void buildSeat() {mBike.setSeat("真皮车座");}@Overridepublic Bike createBike() {return mBike;}
}
public class Director {private Builder mBuilder;public Director(Builder builder) {this.mBuilder = builder;}public Bike construct() {mBuilder.buildFrame();mBuilder.buildSeat();return mBuilder.createBike();}
}
public class Client {public static void main(String[] args) {showBike(new HelloBuilder());showBike(new MobikeBuilder());}private static void showBike(Builder builder) {Director director = new Director(builder);Bike bike = director.construct();System.out.println(bike.getFrame());System.out.println(bike.getSeat());}
}

省略抽象的 Builder 类

如果系统中只需要一个具体的建造者,可以省略抽象建造者

省略 Director 类

如果只有一个具体建造者,并且简化了抽象建造者,那么可以省略掉指导者。让建造者直接扮演指导者。

三、用法2 控制对象构造方法、限制参数关系

建造者模式除了用来分离复杂对象的构建过程,还可以在构建对象的同时用来控制对象的构造方法,限制对象的构建参数关系。
使用场景

  1. 场景 1 类的构造方法过长,降低了代码可读性容易搞错参数。
  2. 场景 2 使用 setter 方法优化场景 1,但是这样会导致遗漏对象的必填属性并且无法实现前后关联属性的设置。
public class ResourcePoolConfig{private String name;private int maxTotal;private int maxIdle;private int minIdle;//如果builder是内部类,这里就可以使用private修饰public ResourcePoolConfig (Builder builder){this.name=builder.name;this.maxTotal=builder.maxTotal;this.maxIdle=builder.maxIdle;this.minIdle=builder.minIdle;}
}
public class Builder{private static final int DEFAULT_MAX_TOTAL=9;private String name;private int maxTotal;//其他字段省略public ResourcePoolConfig build(){//可以写校验逻辑return new ResourcePoolConfig(this);}public Builder setMaxTotal(int maxTotal){//校验if(maxTotal<0){throw new RuntimeException();}this.maxTotal=maxTotal;}}

Guava 中使用建造者模式构建 cache 来进行参数校验

Guava本地缓存框架是Google的Guava库提供的一种高性能、线程安全的本地缓存实现。它旨在帮助Java开发者有效地管理和存储数据在内存中,从而加速数据访问速度并减轻对底层数据存储系统的压力。Guava Cache具有丰富的特性和灵活性,使其成为处理高并发和高性能需求场景下的理想选择。下面是一些关键特性和使用方法的概述:
主要特性:

  1. 自动加载(Loading Cache): Guava允许你定义一个CacheLoader,当缓存中没有请求的键对应的值时,自动调用加载数据的方法并插入到缓存中。这样可以实现懒加载,并且保持代码的简洁性。
  2. 缓存过期: 支持基于时间(如访问后多久过期、写入后多久过期)或基于大小(如缓存容量达到上限后开始移除旧的条目)的过期策略,自动管理缓存项的有效性,避免内存泄漏。
  3. 统计信息: 提供丰富的统计信息,比如命中率、平均加载时间等,帮助监控和优化缓存性能。
  4. 软引用和弱引用: Guava Cache允许使用软引用或弱引用存储缓存项,这样当JVM内存紧张时,这些引用可以被垃圾收集器回收,以避免内存溢出。
  5. 并发支持: 内部实现高度并发安全,利用锁和其他同步机制确保在多线程环境下的正确性和高效性。
  6. 可自定义的缓存行为: 通过CacheBuilder,你可以自定义缓存的各种行为,比如缓存过期策略、最大容量、加载机制、统计开启与否等。

guava 中就通过建造者模式来解决了构造参数过长的问题,因为如果先构造无参对象再通过 SET 赋值参数则无法实现必要的参数校验;
Google Guava 中构建内存缓存的案例如下;

public class CacheDemo{public static void main(String[] args){Cache<String,String> cache = CacheBuilder.newBuilder().initialCapacity(100).maximumSize(100).expireAfterWrite(10,TimeUnit.MINUTES).build();cache.put("key1","value1");String value = cache.getIfPresent("key1");System.out.println(value);}
}

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

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

相关文章

一次改SQLMAP的操作

前言 sqlmap这个工具&#xff0c;相信各位大佬们都不陌生&#xff0c;但sqlmap虽好&#xff0c;也时常会有些实际存在但无法注入的地方&#xff0c;这时候就需要我们改它的配置了&#xff0c;今天就以本人遇到的事件进行阐述。 正文 确认注入点 通过一系列测试最终确定这里…

【Python】Flask问答系统Demo项目

学习视频 我是跟着知了传课学的Flask&#xff0c;起初了解Flask还是GPT告诉我的&#xff0c;现在可以说用Flask做后端是真的方便&#xff01; https://www.bilibili.com/video/BV17r4y1y7jJ 项目结构与下载 FlaskOA&#xff08;项目文件夹&#xff09; │ app.py │ conf…

01_基于人脸的常见表情识别实战_深度学习基础知识

1. 感知机 感知机通常情况下指单层的人工神经网络,其结构与 MP 模型类似(按照生物神经元的结构和工作原理造出来的一个抽象和简化了模型,也称为神经网络的一个处理单元) 假设由一个 n 维的单层感知机,则: x 1 x_1 x1​ 至 x n x_n xn​ 为 n 维输入向量的各个分量w 1 j…

掌握Google搜索结果获取

在数据驱动的决策世界中&#xff0c;获取准确而全面的信息至关重要。Google 搜索结果抓取是一种强大的技术&#xff0c;可以让企业、调查人员和研究人员从搜索引擎结果中提取可靠的数据。本综合指南将深入研究 Google 搜索结果的最佳实践、工具和道德考量&#xff0c;以确定能够…

【初阶数据结构】深入解析顺序表:探索底层逻辑

&#x1f525;引言 本篇将深入解析顺序表:探索底层逻辑&#xff0c;理解底层是如何实现并了解该接口实现的优缺点&#xff0c;以便于我们在编写程序灵活地使用该数据结构。 &#x1f308;个人主页&#xff1a;是店小二呀 &#x1f308;C语言笔记专栏&#xff1a;C语言笔记 &…

快递一键查询,只需快递单号,轻松掌握全程物流信息,让您的包裹追踪无忧!

在快节奏的现代生活中&#xff0c;快递已经成为我们生活中不可或缺的一部分。无论是网购的宝贝、亲朋好友寄来的礼物&#xff0c;还是工作中的紧急文件&#xff0c;快递都承载着我们的期待和需要。然而&#xff0c;面对众多的快递公司和复杂的查询流程&#xff0c;如何快速、准…

浅谈DALL-E2

目录 1.概述 2.诞生背景 3.作用 4.版本历史 5.模型和技术 6.应用场景 6.1.十个应用场景 6.2.游戏开发 7.接口 8.未来展望 9.总结 1.概述 DALL-E2 是由 OpenAI 开发的一个图像生成模型&#xff0c;可以根据文本描述生成高质量的图像。DALL-E2 是 DALL-E 的升级版&am…

jupyter notebook使用conda环境

pycharm中安装过可以使用的库在jupyter notebook中导入不进来 1 检查pycharm中安装的库的位置 2 检查jupyter notebook中安装的库的位置 3 查看jupyter notebook内核名字 可以看到jupyter notebook中内核名字叫ipykernel 4 安装ipykernel 在pycharm的terminal中 pip instal…

Polar Web【中等】反序列化

Polar Web【中等】反序列化 Contents Polar Web【中等】反序列化思路&探索EXPPHP生成PayloadGET传递参数 运行&总结 思路&探索 一个经典的反序列化问题&#xff0c;本文采用PHP代码辅助生成序列字符串的方式生成 Payload 来进行手动渗透。 打开站点&#xff0c;分析…

fastadmin/thinkPHP5.0的框架使用注意事项

0.主要链接 一张图解析表格 数据表规划一定要做好,省的做的时候很乱,一会要改一下,就特别麻烦 在线命令生成crud的时候一定不要填写自定义控制器名,要让他自己生成,否则后面你要修改东西还需要再找.默认的永远能知道在哪里 在线命令生成的时候,可以试着删除一下(不会成功),但…

Shell脚本01

一、shell脚本 脚本就是可运行的代码的集合&#xff0c;脚本语言&#xff08;计算机语言&#xff09;。 脚本的特点&#xff1a;从上到下&#xff0c;按行执行。 shell 脚本就是在shell环境&#xff08;bin/bash&#xff09;bash就是shell解释器&#xff0c;linux环境下的编…

重邮计算机网络803-(1)概述

目录 一.计算机网络向用户提供的最重要的功能 二.互联网概述 1.网络的网络 2.计算机网络的概念 3. 互联网发展的三个阶段 4.制订互联网的正式标准要经过以下的四个阶段 5.互联网的组成&#xff08;功能&#xff09; 6.互联网功能 7.互联网的组成&#xff08;物理&…

物联网TCP、UDP、CoAP、LwM2M、MQTT协议简单对比

一、前言 目前物联网行业有TCP、UDP、CoAP、LwM2M、MQTT、Modbus系列、JT808、HTTP、TLINK、ISAPI等协议&#xff0c;本文先对其中的几款协议进行介绍。具体关系见下图&#xff1a; 传输层协议&#xff1a;TCP、UDP&#xff1b;应用层协议&#xff1a;CoAP、LwM2M、MQTT、Modbu…

Go微服务: 关于消息队列的选择和分类以及使用场景

消息队列概述 在分布式系统和微服务架构中&#xff0c;消息队列&#xff08;Message Queue&#xff09;是一个核心组件&#xff0c;用于在不同的应用程序或服务之间异步传递消息在 Go 语言中&#xff0c;有多种实现消息队列的方式&#xff0c;包括使用开源的消息队列服务&…

OSI七层网络参考模型

一、物理层 我们要发送出去的数据在计算机里只不过是无数的0和1&#xff0c;0或1就叫做比特&#xff0c;物理层就是把这些比特用不同的媒介传输出去&#xff0c;可以用电、光或者其他形式的电磁波来表示和传输信号&#xff0c;数据从网络接口出去以后&#xff0c;会经过不同的网…

一文带你入门 - Qt绘图QPainter

QPaintEvent绘图事件: QPaintEvent 是 Qt 框架中一个重要的事件类&#xff0c;专门用于处理绘图事件。当 Qt 视图组件需要重绘自己的一部分时&#xff0c;就会产生 QPaintEvent 事件。这通常发生在以下几种情况&#xff1a; 1. 窗口第一次显示时&#xff1a;当窗口或控件第一次…

计算机组成原理(二)

ACC&#xff08;累加器&#xff09;&#xff1a; 用于存储高位部分 MQ&#xff08;乘数-商寄存器&#xff09;&#xff1a; 用于存储低位部分。在除法中保存商&#xff0c;在乘法中保存乘数&#xff0c;所以也叫乘商寄存器 左移 8 位&#xff08;相当于乘以 256&#xff09…

AI产品经理的转行之路,如何迈向年薪80w的职业高峰?

前言 在当今科技日新月异的时代&#xff0c;AI产品经理作为一个炙手可热的职业&#xff0c;吸引了众多向往高薪与前沿领域结合的求职者的目光。年薪80万的诱惑力无疑是巨大的&#xff0c;但不少自学中的朋友发现&#xff0c;即便涉猎广泛的产品知识&#xff0c;想要顺利转型成…

掌握Python的全方位教程,2024年最新版本,初学者必备指南

哈喽&#xff0c;大家好&#xff01;热烈欢迎你迈出成为python开发者的第一步。我想这一定非常激动人心&#xff0c;对吧&#xff1f;无论你是刚刚开始学习编程&#xff0c;还是曾经用过其他语言有一定的编程经验&#xff0c;本书中课程将帮助你加速实现你学习python的目标。作…

2024第十六届亚洲水技术展览会Aquatech China

Aquatech China 2024第十六届亚洲水技术展览会 专注水行业覆盖全领域—荷兰阿姆斯特丹水展中国展 2024.12.11-13 上海新国际博览中心 展会背景 Aquatech品牌创立于1968年。作为水处理行业历史悠久 的展览会&#xff0c;荷兰国际水处理展览会(Aquatech Amsterdam)至今已有近55…