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

设计模式——适配器模式

引入实例

说起适配器其实在我们的生活中是非常常见的,比如:学校的宿舍的电压都比较低,而有的学生想使用大功率电器,宿舍的就会跳闸,然而如果你使用一个适配器(变压器)就可以使用了(温馨提示宿舍使用大功率电器不太安全,容易引起火灾,希望大家谨慎使用)。

又比如说,有的插座都是三孔的,而我们用的大部分电器是两孔的,这时我们可以使用一个适配器,适配器本身是三孔的,它可以直接插到三孔的插头上,适配器本身可以提供一个两孔的插座,然后我们就可以插到适配器上了,这样我们原本只能插到两孔上的插头就能用三孔的插座了。

适配器模式的相关概念

适配器模式的正式定义

适配器模式(Adapter Pattern)是作为两个不兼容的接口之间的桥梁。这种类型的设计模式属于结构型模式,它结合了两个独立接口的功能。

适配器模式分为

  • 类适配器模式
  • 对象适配器模式

适配器模式的结构

适配器模式里面总共拥有三个角色,它们分别是:

  • 目标(Target)接口:当前系统业务所期待的接口,它可以是抽象类或接口。
  • 适配者(Adaptee)类:它是被访问和适配的现存组件库中的组件接口。
  • 适配器(Adapter)类:它是一个转换器,通过继承(类适配器模式)或引用适配者的对象(对象适配器模式),把适配者接口转换成目标接口(也就是使用转换器将三头的插座转换成适合我们使用的两头插座),让客户按目标接口的格式访问适配者。

注意事项:适配器不是在详细设计时添加的,而是解决正在服役的项目的问题。

类适配器

类适配器的原理就是通过继承来实现适配器功能。

让Adapter实现Target接口,并且继承Adaptee,这样Adapter就具备Target和Adaptee的特性,就可以将两者进行转化。

举例:以不同设备使用不同交流电为例,通过电源适配器进行转换说明。

创建目标角色(Target)

public interface Target {int out();
}

创建源角色(Adaptee)

public class Adaptee{public int input() {System.out.println("输入交流电: 220V");return 220;}
}

创建适配器(Adapter)

public class Adapter extends Adaptee implements Target {@Overridepublic int out() {int input220V = super.input();int output = input220V / 2;System.out.println("输出交流电: " + output + "V");return output;}
}

客户端调用

public static void main(String[] args) {Target adapter = new Adapter();int result = adapter.out();System.out.println(result);
}

输入交流电: 220V
输出交流电: 110V
110

对象适配器

对象适配器的原理就是通过组合来实现适配器功能。

让Adapter实现Target接口,然后内部持有Adaptee实例,然后再Target接口规定的方法内转换Adaptee。

创建目标角色(Target)

public interface Target {int out();
}

创建源角色(Adaptee)

public class Adaptee{public int input() {System.out.println("输入交流电: 220V");return 220;}
}

创建适配器(Adapter)

public class Adapter implements Target {private Adaptee adaptee;public Adapter(Adaptee adaptee) {this.adaptee = adaptee;}@Overridepublic int out() {int output = adaptee.input() / 2;System.out.println("输出交流电: " + output + "V");return output;}
}

客户端调用

    public static void main(String[] args) {Target adapter = new Adapter(new Adaptee());int result = adapter.out();System.out.println(result);}

输入交流电: 220V
输出交流电: 110V
110

接口适配器

接口适配器的使用场景是解决接口方法过多,如果直接实现接口,那么类会多出许多空实现的方法,类显得很臃肿。此时,使用接口适配器就能让我们只实现我们需要的接口方法,目标更清晰。

接口适配器的主要原理就是原理利用抽象类实现接口,并且空实现接口众多方法。

创建目标角色(Target)

public interface Target {int out1();int out2();int out3();int out4();
}

创建源角色(Adaptee)

public class Adaptee{public int input() {System.out.println("输入交流电: 220V");return 220;}
}

创建适配器(Adapter)

public class Adapter implements Target {protected Adaptee adaptee;public Adapter(Adaptee adaptee){this.adaptee = adaptee;}@Overridepublic int out1() {int input220V = adaptee.input();int output = input220V / 1;System.out.println("输出交流电: " + output + "V");return output;}@Overridepublic int out2() {int input220V = adaptee.input();int output = input220V / 2;System.out.println("输出交流电: " + output + "V");return output;}@Overridepublic int out3() {return 0;}@Overridepublic int out4() {return 0;}
}

客户端调用

    public static void main(String[] args) {Target adapter = new Adapter(new Adaptee());adapter.out1();System.out.println("---------------------");adapter.out2();System.out.println("---------------------");Target adapter2 = new Adapter(new Adaptee()) {@Overridepublic int out3() {int input220V = adaptee.input();int output = input220V / 3;System.out.println("输出交流电: " + output + "V");return output;}};adapter2.out3();System.out.println("---------------------");Target adapter3 = new Adapter(new Adaptee()) {@Overridepublic int out4() {int input220V = adaptee.input();int output = input220V / 4;System.out.println("输出交流电: " + output + "V");return output;}};adapter3.out4();}

输入交流电: 220V
输出交流电: 220V
---------------------
输入交流电: 220V
输出交流电: 110V
---------------------
输入交流电: 220V
输出交流电: 73V
---------------------
输入交流电: 220V
输出交流电: 55V

优缺点

适配器模式优点:

  • 可以让任何两个没有关联的类一起运行。
  • 提高了类的复用。
  • 增加了类的透明度。
  • 灵活性好。

适配器模式缺点:

  • 过多地使用适配器,会让系统非常零乱,不易整体进行把握。比如,明明看到调用的是 A 接口,其实内部被适配成了 B 接口的实现,一个系统如果太多出现这种情况,无异于一场灾难。因此如果不是很有必要,可以不使用适配器,而是直接对系统进行重构。
  • 由于 JAVA 至多继承一个类,所以至多只能适配一个适配者类,而且目标类必须是抽象类。

优点 :

  • 类适配器模式优点:由于适配器类是适配者类的子类,因此可以在适配器类中置换一些适配者的方法,使得适配器的灵活性更强。
  • 对象适配器模式优点:一个对象适配器可以把多个不同的适配者适配到同一个目标,也就是说,同一个适配器可以把适配者类和它的子类都适配到目标接口。

缺点:

  • 类适配器模式缺点:对于Java、C#等不支持多重继承的语言,一次最多只能适配一个适配者类,而且目标抽象类只能为抽象类,不能为具体类,其使用有一定的局限性,不能将一个适配者类和它的子类都适配到目标接口。
  • 对象适配器模式缺点:与类适配器模式相比,要想置换适配者类的方法就不容易。如果一定要置换掉适配者类的一个或多个方法,就只好先做一个适配者类的子类,将适配者类的方法置换掉,然后再把适配者类的子类当做真正的适配者进行适配,实现过程较为复杂。

类适配器和对象适配器的区别:

  • 前者类之间的耦合度比后者高(这是因为类适配器模式使用的是继承的方式,而对象适配器模式使用的是聚合或者组合的方式)。
  • 类适配器模式要求程序员了解现有组件库中的相关组件的内部结构,所以应用相对较少些,用的更多的还是对象适配器模式。

应用场景

  1. 当一个系统需要使用另一个系统的接口时,但是两个系统的接口不兼容,可以使用适配器模式进行接口转换。
  2. 在数据处理方面,适配器模式可以用于将不同格式的数据适配到一个标准的数据格式上。
  3. 当我们需要复用一些已有的类的时候,这些类的接口与我们需要的接口不兼容,可以使用适配器将这些类的接口转换成我们需要的接口,从而实现类的复用。
  4. 适配器模式可以用于封装有缺陷的接口设计,使得客户可以通过适配器来使用这些缺陷的接口,而无需直接与其交互。
  5. 替换依赖的外部系统,使得系统可以在不修改源代码的情况下适应新的外部系统。
http://www.lryc.cn/news/129916.html

相关文章:

  • 如何区分闰年与平年
  • 中间件(下)
  • LVS-DR的RS进行ARP抑制的原因和LVS持久连接配置
  • 【HarmonyOS】codelab在hvigor版本2.4.2上无法运行问题
  • MySQL- sql语句基础
  • 【目标检测中对IoU的改进】GIoU,DIoU,CIoU的详细介绍
  • 【环境配置】Windows10终端和VSCode下能够直接打开Anaconda-Prompt
  • 稚晖君人形机器人问世:大模型加持,会自己换胳膊,要上生产线造车
  • 变更通知在开源SpringBoot/SpringCloud微服务中的最佳实践
  • 亚马逊产品排名关键因素解析,通过测评干预需要具备哪些条件
  • leetcode原题:绘制直线(位运算)
  • jenkins 安装和通过gitee 拉取PHP项目
  • 解析TCP/IP协议的分层模型
  • ARM M33架构入门
  • CentOS系统环境搭建(四)——Centos7安装Java
  • Arduino MQTT客户端库PubSubClient快速入门
  • 视频集中存储/云存储/磁盘阵列EasyCVR平台接入RTSP设备出现离线情况的排查
  • 部署Springboot项目注意事项
  • 深度解析:DDoS攻击与先进防御策略
  • NLP | 论文摘要文本分类
  • Linux / Ubuntu磁盘扩容
  • 【ChatGPT 指令大全】怎么使用ChatGPT来辅助知识学习
  • URL编码指南
  • Java mail邮件开发 OA办公系统
  • ElasticSearch的客户端操作
  • 如何快速的合并多个PPT使之成为一个PPT?
  • 【微信小程序】列表滚动触底更新实现
  • 2023全国大学生数学建模竞赛A题B题C题D题E题思路+模型+代码+论文
  • Git常见操作
  • thinkphp6前后端验证码分离以及验证