适配器模式之对象适配器

摘要:
适配器模式也称为包装器,用于将类的接口转换为客户需要的另一个接口。适配器模式的关键是建立一个适配器,它实现目标接口并包含适配器的引用。这里有一个简单的问题来描述适配器模式中涉及的角色。要解决上述问题,请使用适配器模式设计几个类。

  问题导入:比如有A型螺母和B型螺母,那么用户可以再A型螺母上直接使用按着A型螺母生产的A型螺丝,同样也可以在B型螺母上直接使用按着B型螺母标准生产的B型螺丝。但是由于A型螺母和B型螺母的标准不一样,用户在A型螺母上不能直接使用B型的螺丝,反之也一样。该如何达到这个目的呢?

  使用适配器就可以解决这个问题:生产一种“A型螺母适配器”,这种A型螺母适配器的前端符合A型螺母标准要求,可以拧在A型螺母上,后端又焊接了一个B型螺母。这样用户就可以借助A型螺母适配器在A型螺母上使用B型的螺丝了。

  适配器模式又称为包装器,是用来将一个类的接口转换成客户希望的另外一个接口。这可以使得原本由于接口不兼容而不能一起工作的那些类可以一起工作。适配器模式的关键是建立一个适配器,这个适配器实现了目标接口并且包含了被适配者的引用。

  适配器模式的三种角色:

  一、目标:目标是一个接口,该接口是客户想要使用的接口。

  二、被适配者:被适配者是一个已经存在的接口或抽象类,这个接口接口或者抽象类需要适配。

  三、适配器:适配器是一个类,该类实现了目标接口并且包含有被适配者的引用,即适配器的职责是对适配者接口或抽象类与目标接口进行适配。

  以下通过一个简单的问题来描述适配器模式中所涉及的各个角色。

  用户已经有一个两厢的插座,但是最近用户又有了一个新的三厢插座。用户现有一台洗衣机和一台电视机,洗衣机是三厢插头,而电视机是两厢插头。现在用户想用心的三厢插座来使用洗衣机和电视机,即用心的三厢插座为洗衣机和电视机接通电流。

  针对以上问题,使用适配器模式设计若干个类。

  1.目标

  本问题是使用三厢插座来为电视机和洗衣机接通电流,所以目标是三厢插座。把三厢插座设置为一个接口:

1 package com.adatpe;
2 
3 //适配目标:三相插座
4 public interface ThreeElectricOutlet {
5     void connectElectricCurrent();
6 }

  2.被适配者

  对于本问题,用户是想要用三厢插座为两厢插头的电视机接通电流,所以被适配者应该是两厢插座,也设置为一个接口:

1 package com.adatpe;
2 
3 //被适配者:两相插座
4 public interface TwoElectricOutlet {
5     void connectElectricCurrent();
6 }

  3.适配器

  该适配器实现了目标接口三厢插座ThreeElectricOutlet,同时又包含了两厢插座TwoElectricOutlet的引用:

 1 package com.adatpe;
 2 
 3 //适配器:实现目标接口
 4 public class ThreeElectricAdapter implements ThreeElectricOutlet {
 5     //适配器包含被适配者的引用
 6     private TwoElectricOutlet outlet;
 7     public ThreeElectricAdapter(TwoElectricOutlet outlet) {
 8         this.outlet = outlet;
 9     }
10     public void connectElectricCurrent() {
11         outlet.connectElectricCurrent();
12     }
13 
14 }

  下列应用程序中,Application.java使用了适配器模式中所涉及的类,应用程序负责用Wash类创建一个对象来模拟一台洗衣机,使用TV类创建一个对象来模拟一台电视机

使用ThreeElectricOutlet接口变量调用Wash对象的connectElectricCurrent()方法,并借助适配器调用TV对象的connectElectricCurrent()方法,即用三厢插座分别为洗衣机和电视机接通电流。

  

 1 package com.adatpe;
 2 
 3 public class Application {
 4     public static void main(String[] args) {
 5         ThreeElectricOutlet outlet; //目标接口(三相插座)
 6         Wash wash = new Wash();     //洗衣机
 7         outlet = wash;              //洗衣机插在三相插座上
 8         System.out.println("使用三相插座接通电流");
 9         outlet.connectElectricCurrent();    //接通电流开始洗衣服
10         TV tv = new TV();           //电视机
11         ThreeElectricAdapter adapter = new ThreeElectricAdapter(tv); //把电视插在适配器上面
12         outlet = adapter;           //再把适配器插在三厢插座上
13         System.out.println("使用三厢插座接通电流");
14         outlet.connectElectricCurrent();  //接通电流,开始播放电视节目
15     }
16 }
17 
18 //洗衣机使用三相插座
19 class Wash implements ThreeElectricOutlet{
20     private String name;
21     public Wash() {
22         name = "黄河洗衣机";
23     }
24     public Wash(String name){
25         this.name = name;
26     }
27     public void connectElectricCurrent() {
28         turnOn();
29     }
30     public void turnOn(){
31         System.out.println(name+"开始洗衣服了");
32     }
33 }
34 
35 
36 //电视机使用两厢插座
37 class TV implements TwoElectricOutlet{
38     private String name;
39     public TV() {
40         name = "长江电视机";
41     }
42     public TV(String name){
43         this.name = name;
44     }
45     public void connectElectricCurrent() {
46         turnOn();
47     }
48     public void turnOn(){
49         System.out.println(name+"开始播放电视节目");
50     }
51     
52 }

运行结果为:

使用三相插座接通电流
黄河洗衣机开始洗衣服了
使用三厢插座接通电流
长江电视机开始播放电视节目

下面举个双向适配器的例子

  在适配器模式中,如果Adapter角色同时实现目标接口和被适配者接口,并包含目标接口和被适配接口的引用,那么该适配器就是一个双向适配器。使用双向适配器,用户既可以用新的接口又可以用已有的接口。在以上例子中,如果用户希望能有三厢插座来接通洗衣机和电视机的电流,有可以用两厢插座来接通洗衣机和电视机的电流,那么就必须使用一个双向适配器。具体代码如下:

 1 package com.adatpe;
 2 
 3 public class ThreeAndTwoElectricAdapter implements ThreeElectricOutlet,
 4         TwoElectricOutlet {
 5     private ThreeElectricOutlet threeElectricOutlet;
 6     private TwoElectricOutlet twoElectricOutlet;
 7     public ThreeAndTwoElectricAdapter(ThreeElectricOutlet threeOutlet,TwoElectricOutlet twoOutlet) {
 8         threeElectricOutlet = threeOutlet;
 9         twoElectricOutlet = twoOutlet;
10     }
11     public ThreeAndTwoElectricAdapter(TwoElectricOutlet twoOutlet,ThreeElectricOutlet threeOutlet){
12         threeElectricOutlet = threeOutlet;
13         twoElectricOutlet = twoOutlet;
14     }
15     public void connectElectricCurrent() {
16         if(this instanceof ThreeElectricOutlet){
17             twoElectricOutlet.connectElectricCurrent();//twoElectricOutlet是被适配的接口
18         }
19         if(this instanceof TwoElectricOutlet){
20             threeElectricOutlet.connectElectricCurrent(); //threeElectricOutlet是被适配的接口
21         }
22     }
23     public static void main(String[] args) {
24         ThreeElectricOutlet threeOutlet;
25         TwoElectricOutlet twOutlet;
26         Wash wash = new Wash();
27         TV tv = new TV();
28         ThreeAndTwoElectricAdapter adapter = new ThreeAndTwoElectricAdapter(wash,tv);
29         threeOutlet = adapter;
30         System.out.println("使用三厢插座接通电源");
31         threeOutlet.connectElectricCurrent();
32         twOutlet = adapter;
33         System.out.println("使用两厢插座接通电源");
34         twOutlet.connectElectricCurrent();
35     }
36 
37 }


运行结果为:

使用三厢插座接通电源
长江电视机开始播放电视节目
黄河洗衣机开始洗衣服了
使用两厢插座接通电源
长江电视机开始播放电视节目
黄河洗衣机开始洗衣服了

这样就实现了即可以用三厢插座又可以用两厢插座来为电视机和洗衣机接通电流了。

使用适配器模式主要有以下优点:

  1.目标和被适配者是完全解耦的关系。

  2.适配器模式满足“开--闭原则”,当添加一个实现了Adapter接口的新类时,不必修改Adapter,Adapter就能对这个新类的实例进行适配。

  

  

  

免责声明:文章转载自《适配器模式之对象适配器》仅用于学习参考。如对内容有疑问,请及时联系本站处理。

上篇vue2.0之axios使用详解ccf-集合竞价-201412-3下篇

宿迁高防,2C2G15M,22元/月;香港BGP,2C5G5M,25元/月 雨云优惠码:MjYwNzM=

相关文章

jweixin-1.1.0.js微信接口“分享给朋友”文字和图片配置

在npm官网找到了:微信官方 js-sdk CommonJS 版https://www.npmjs.com/package/weixin-js-sdk 步骤一:引入JS文件在需要调用JS接口的页面引入如下JS文件,(支持https):http://res.wx.qq.com/open/js/jweixin-1.0.0.js备注:支持使用 AMD/CMD 标...

DPDK — 架构解析

目录 文章目录 目录 前文列表 DPDK 架构 内核态模块 IGB_UIO KNI PMD DPDK Lib(核心部件库) 组件代码 平台相关模块 Classify 库 QoS 库 前文列表 《DPDK — 安装部署》《DPDK — 数据平面开发技术》 DPDK 架构 内核态模块: IGB_UIO: KNI 用户态函数库以及网卡驱动程序...

接口性能测试方案

一、 性能测试术语解释 1. 响应时间 响应时间即从应用系统发出请求开始,到客户端接收到最后一个字节数据为止所消耗的时间。响应时间按软件的特点再可以细分,如对于一个 C/S 软件的响应时间可以细分为网络传输时间、应用服务器处理时间、数据库服务器处理时间。另外客户端自身也存在着解析时间、界面绘制呈现时间等。  响应时间主要站在客户端角度来看的一个性能指标,它...

一天一个设计模式——Adapter适配器模式(Wrapper模式)

一、模式说明   在现实生活中,当需要将两种设备连接起来,但是两个设备的接口规范又不一致(比如电脑上只有Type-C接口,但是你的显示器是HDMI接口),这时候就需要一个适配器,适配器一端连接电脑,一端连接屏幕。有了这个适配器,我们不需要重新买HDMI接口电脑的电脑,就可以达到我们连接外置显示器的目的。   在程序设计领域,很多时候我们的工作是在现有类的基...

Web后台快速开发框架(.NET Core)

Web后台快速开发框架(.NET Core) Coldairarrow 目录 目录 第1章    目录    1 第2章    简介    3 第3章    基础准备    4 3.1    开发环境要求    4 3.2    基础数据库构建    4 3.3    运行    5 第4章    详细教程    7 4.1    代码架构    ...

Spring Boot中集成Spring Security 专题

  check to see if spring security is applied that the appropriate resources are permitted: @Configuration public class WebSecurityConfiguration extends WebSecurityConfigurer...