设计模式——适配器设计模式

设计模式——适配器设计模式

  • 适配器设计模式
    • 1.1 基本介绍
    • 1.2 工作原理
    • 1.3 类适配器模式
      • 1.3.1 基本介绍
      • 1.3.2 示例
      • 1.3.3 代码实现
      • 1.3.4 注意事项
    • 1.4 对象适配器模式
      • 1.4.1 基本介绍
      • 1.4.2 示例
      • 1.4.3 代码实现
      • 1.4.4 注意事项
    • 1.5 接口适配器模式
      • 1.5.1 基本介绍
      • 1.5.2 示例
      • 1.5.3 代码实现
    • 1.6 注意事项

适配器设计模式

1.1 基本介绍

  1. 适配器模式(Adapter Pattem)将某个类的接口转换成客户端期望的另一个接口表示,主的目的是兼容性,让原本因接口不匹配不能一起工作的两个类可以协同工作。其别名为包装器(Wrapper)
  2. 适配器模式属于结构型模式
  3. 主要分为三类:类适配器模式、对象适配器模式、接口适配器模式

1.2 工作原理

  1. 适配器模式:将一个类的接口转换成另一种接口.让原本接口不兼容的类可以兼容
  2. 从用户的角度看不到被适配者,是解耦的
  3. 用户调用适配器转化出来的目标接口方法,适配器再调用被适配者的相关接口方法
  4. 用户收到反馈结果,感觉只是和目标接口交互,如图
    示例1

1.3 类适配器模式

1.3.1 基本介绍

基本介绍:Adapter类,通过继承 src 类,实现dst 类接口,完成src->dst 的适配。

1.3.2 示例

说明:
以生活中充电器的例子来讲解适配器,充电器本身相当于 Adapter,220V 交流电相当于 src(即被适配者),我们的dst(即目标)是 5V 直流电

类图:
phone

1.3.3 代码实现

正常电压220V

public class Voltage220V {public int output220V() {int src = 220;System.out.println("电压=" + src + "V");return src;}
}

转为 手机充电5V电压

public interface IVoltage5V {public int output5V();
}

适配器:

public class VoltageAdapter extends Voltage220V implements IVoltage5V {public int output5V() {int srcV = output220V();int dstV = srcV / 44;return dstV;}
}

手机充电:

public class Phone {public void charging(IVoltage5V iVoltage5V) {int v = iVoltage5V.output5V();if (v == 5) {System.out.println("电压为5V,可以充电~");} else if (v > 5) {System.out.println("电压大于5V,不可以充电~");}}
}

客户端调用:

public class Client {public static void main(String[] args) {Phone phone = new Phone();phone.charging(new VoltageAdapter());}
}

打印输出:

电压=220V
电压为5V,可以充电~

1.3.4 注意事项

  1. Java 是单继承机制,所以类适配器需要继承 src 类这一点算是一个缺点,因为这要求 dst 必须是接口,有一定局限性;
  2. src 类的方法在 Adapter 中都会暴露出来,也增加了使用的成本。
  3. 由于其继承了 src 类,所以它可以根据需求重写 src 类的方法,使得 Adapter 的灵活性增强了。

1.4 对象适配器模式

1.4.1 基本介绍

  1. 基本思路和类的适配器模式相同,只是将 Adapter 类作修改,不是继承 src 类,而是持有 src 类的实例,以解决兼容性的问题。 即:持有 src 类,实现 dst 类接口,完成 src->dst 的适配
  2. 根据“合成复用原则”,在系统中尽量使用关联关系(聚合)来替代继承关系。
  3. 对象适配器模式是适配器模式常用的一种

1.4.2 示例

说明:
以生活中充电器的例子来讲解适配器,充电器本身相当于 Adapter,220V 交流电相当于 src(即被适配者),我们的dst(即目标)是 5V 直流电,用对象适配器模式实现

只需要修改适配器,类图:
示例2

1.4.3 代码实现

只需要修改适配器的代码,其他的代码和上面一致
适配器,拥有220V的属性,不需要继承


public class VoltageAdapter implements IVoltage5V {private Voltage220V voltage220V;public VoltageAdapter(Voltage220V voltage220V) {this.voltage220V = voltage220V;}public int output5V() {int dstV = 0;if (voltage220V != null) {int srcV = voltage220V.output220V();System.out.println("使用对象适配模式,进行适配!");dstV = srcV / 44;System.out.println("适配完成,输出的电压=" + dstV + "V");}return dstV;}
}

Client调用:

public class Client {public static void main(String[] args) {Phone phone = new Phone();phone.charging(new VoltageAdapter(new Voltage220V()));}
}

结果打印:

电压=220V
使用对象适配模式,进行适配!
适配完成,输出的电压=5V
电压为5V,可以充电~

1.4.4 注意事项

  1. 对象适配器和类适配器其实算是同一种思想,只不过实现方式不同。根据合成复用原则,使用组合替代继承,所以它解决了类适配器必须继承 src 的局限性问题,也不再要求 dst必须是接口。
  2. 使用成本更低,更灵活

1.5 接口适配器模式

1.5.1 基本介绍

  1. 一些书籍称为:适配器模式(Default Adapter Pattern)或缺省适配器模式
  2. 核心思路:当不需要全部实现接口提供的方法时,可先设计一个抽象类实现接口,并为该接口中每个方法提供一个默认实现(空方法),那么该抽象类的子类可有选择地覆盖父类的某些方法来实现需求
  3. 适用于一个接口不想使用其所有的方法的情况。

1.5.2 示例

说明:
示例3

1.5.3 代码实现

接口:

public interface Interface4 {public void m1();public void m2();public void m3();public void m4();
}

抽象类:

public class AbsAdapter implements Interface4{public void m1() {}public void m2() {}public void m3() {}public void m4() {}
}

实现:

public class Client {public static void main(String[] args) {AbsAdapter absAdapter = new AbsAdapter(){@Overridepublic void m1() {System.out.println("使用了m1方法~");}};absAdapter.m1();absAdapter.m2();}
}

输出打印:

使用了m1方法~

1.6 注意事项

  1. 三种命名方式,是根据 src 是以怎样的形式给到 Adapter(在 Adapter 里的形式)来命名的。
  2. 类适配器:以类给到,在 Adapter 里,就是将 src 当做类,继承
    对象适配器:以对象给到,在 Adapter 里,将src 作为一个对象,持有
    接口适配器:以接口给到,在 Adapter 里,将 src 作为一个接口,实现
  3. Adapter 模式最大的作用还是将原本不兼容的接口融合在一起工作。
  4. 实际开发中,实现起来不拘泥于我们讲解的三种经典形式

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

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

相关文章

如何处理Java中数据结构(如HashMap)导致的性能瓶颈

在Java开发过程中,HashMap 是一种常用的数据结构,它提供了高效的键值对存储和快速的查找、插入和删除操作。然而,在某些情况下,HashMap 可能会导致性能瓶颈。本文将探讨这些性能瓶颈的成因,并提供一些优化策略。 一、…

Webkit简介以及工作流程

Webkit简介 WebKit是一个开源的浏览器引擎,最初由苹果公司基于KHTML(K Desktop Environment的HTML渲染引擎)开发,并广泛应用于Safari浏览器。随着时间的推移,WebKit也被其他多款浏览器和应用所采用,成为We…

pudb: Python的图形化调试器

文章目录 pudb原理基础使用安装pudb启动pudb界面介绍常用操作 高级使用条件断点表达式求值自定义布局搜索和过滤插件和扩展 结论 pudb原理 pudb是一个基于文本的图形化Python调试器,它结合了pdb的强大调试功能与图形用户界面的易用性。pudb通过提供一个可视化的界面…

【操作系统】阻塞队列以及生产者消费者模型

目录 阻塞队列一. 概念二. 标准库中的阻塞队列三. 生产者消费者模型四. 阻塞队列实现 总结 阻塞队列 一. 概念 阻塞队列是⼀种特殊的队列.也遵守"先进先出"的原则. 阻塞队列能是⼀种线程安全的数据结构,并且具有以下特性: 当队列满的时候,继续⼊队列就会阻塞,直到…

Splashtop 在医疗与制药领域的业务增长近五倍

2024年7月10日 加利福尼亚州库比蒂诺 Splashtop 是安全远程访问和 IT 支持解决方案领域的领先企业,该公司今天宣布,在医疗与制药领域业务同比增长492%,取得了里程碑式的成就。快速发展的数字实验室环境和持续的网络安全威胁需要实施无缝、安…

Unity之VS脚本自动添加头部注释Package包开发

内容将会持续更新,有错误的地方欢迎指正,谢谢! Unity之VS脚本自动添加头部注释Package包开发 TechX 坚持将创新的科技带给世界! 拥有更好的学习体验 —— 不断努力,不断进步,不断探索 TechX —— 心探索、心进取&…

模板语法指令语法——02

//指令语法: 1.什么是指定,有什么作用? 指令的职责是,当表达式的值改变时,将其产生的连带影响,响应式的作用语DOM 2.vue框架中的所有指令的名字都以v-开始的 3.插值是写在标签当中用的,指令…

WSGI 服务器教程:`execute` 方法解析

Python WSGI 服务器教程:execute 方法解析 在本文中,我们将详细解析一个用于 WSGI 服务器的 execute 方法。这个方法负责执行 WSGI 应用程序,处理其响应数据,并确保在应用程序执行过程中处理所有必要的清理工作。我们将逐行解释该…

uniapp启动图延时效果,启动图的配置

今天阐述uniapp开发中给启动图做延迟效果,不然启动图太快了,一闪就过去了; 一:修改配置文件:manifest.json "app-plus" : {"splashscreen" : {"alwaysShowBeforeRender" : false,"…

编程语言前途:探索未来的无限可能

编程语言前途:探索未来的无限可能 在科技日新月异的今天,编程语言作为连接人类与计算机世界的桥梁,其前途无疑是充满无限可能与挑战的。本文将从四个方面、五个方面、六个方面和七个方面,深入剖析编程语言的前途,带您…

vivado EDIF_EXTRA_SEARCH_PATHS、EQUALIZATION

EDIF_EXTRA_SEARCH_PATHS 此属性定义了Vivado Design Suite在当前文件集上的搜索路径,以 查找设计引用的EDIF文件。 提示:当Vivado设计套件无法执行以下操作时,在实现过程中会出现以下错误 定位与黑盒关联的EDIF网表。这可以通过定义 EDIF_EX…

法律咨询援助网站

1 项目介绍 1.1 摘要 随着互联网技术的飞速发展,公众对于便捷、高效的法律咨询服务需求日益增长。传统的法律咨询方式已难以满足人们即时性、多样化的咨询需求,促使法律咨询援助网站应运而生。这些平台旨在通过数字化手段,为用户提供法律知…

【TS】Typescript 的泛型

TypeScript 的泛型(Generics)是 TypeScript 的一个非常强大的特性,它允许你在编译时定义组件,这些组件可以工作于多种类型的数据上。泛型可以创建可重用的组件,这些组件是独立于任何特定类型的。这意味着你可以编写灵活…

apache:the requested operation has failed使用httpd -t

Apache24\bin cmd 回车 httpd -t 因为我重新压缩了,记住,重新压缩要使用原路径, 因为你安装的 时候使用的是原路径 还是不行就改个端口,切记修改配置文件httpd.conf先把Tomcat停了 Define SRVROOT "F:\Apache\Apache24&q…

C++类和对象学习笔记

1.类的定义 1.1类定义的格式 class是定义类的关键字,Date为类的名字,{ }中为类的主体,注意定义类结束时后面的分号不能省略。类中的内容称为类的成员;类中的变量称为类的属性或成员变量;类中的函数称为类的方法或者成…

自定义枚举对象序列化规则: 在Json中以枚举的code值表示枚举;枚举序列化时,新增枚举描述字段;String到IEnum的转换

文章目录 引言I 案例分析1.1 接口签名计算1.2 请求对象1.3 枚举对象序列化1.4 创建JavaTimeModule以支持Java 8的时间日期类型序列化和反序列化1.5 请求对象默认值处理II 在JSON中以枚举的code值来表示枚举的实现方式2.1 自定义toString方法返回code2.2 使用@JsonValue注解,只…

adminPage-vue3依赖FormPage说明文档,表单页快速开发,使用思路及范例(Ⅱ)formConfig基础配置项

adminPage-vue3依赖FormPage说明文档,表单页快速开发,使用思路及范例(Ⅱ)formConfig配置项 属性: formConfig(表单项设置)keylabelnoLabeldefaultValuebindchildSlottypeString类型数据(除 time…

IntelliJ IDEA 2024.1.4最新教程!!直接2099!!爽到飞起!!

IntelliJ IDEA 2024.1.4最新破解教程!!直接2099!!爽到飞起!!【资源在末尾】安装馆长为各位看官准备了多个版本,看官可根据自己的需求进行下载和选择安装。https://mp.weixin.qq.com/s/Tic1iR_Xc…

C语言:高级并发操作(线程)

一、线程的概念 线程:进程中的一个实体,是CPU调度和分派的基本单位。线程自己基本上不拥有系统资源,只拥有一点在运行中必不可少的资源(如程序计数器、一组寄存器和栈),但它可以与同属一个进程的其他线程共…

前端文件下载的方式

方式一&#xff1a;a标签直接下载 <a href"链接" >下载</a>一个文件链接&#xff08;一般是服务器上的某个文件&#xff09;&#xff0c;这个链接一般地址栏输入是预览&#xff0c;不是附件下载 如果想改成附件下载&#xff0c;以下两种方式任选一个均…