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

ADAPTER(适配器) ———— 类对象结构型模式

意图

将一个类的接口,转换成客户期望的另一个接口。适配器让原来接口不兼容的类可以合作无间。 现在,我们知道,这个模式可以通过创建适配器进行接口转换,让不兼容的接口变成兼容。这可以让客户从实现的接口解耦。如果在一段时间之后,我们想要改变接口,适配器可以将改变的部分封装起来,客户就不必为了应对不同的接口而每次跟着修改。

适配器模式的本质:转换匹配,复用功能。 适配器通过转换调用已有的实现,从而能把已有的实现匹配成需要的接口,使之能满足客户端的需要。也就是说转换匹配是手段,而复用已有的功能才是目的。

适用性

  • 如果你想要使用一个已经存在的类,但是它的接口不符合你的需求,这种情况可以使用适配器模式,来把已有的实现转换成你需要的接口
  • 如果你想创建一个可以复用的类,这个类可能和一些不兼容的类一起工作,这种情况可以使用适配器模式,到时候需要什么就适配什么
  • (仅适用于“对象”适配器)如果你想使用一些已经存在的子类,但是不可能对每一个子类都进行适配,这种情况可以选用对象适配器,直接适配这些子类的父类就可以了。

结构

“类”适配器使用多重继承对一个接口与另一个接口进行匹配

“类”适配器结构图

“对象”适配器依赖于对象组合

“对象”适配器结构图

  • Target 定义Client使用的与特定领域相关的接口。
  • Client 与符合Target接口的对象协同
  • Adaptee 定义一个已经存在的接口,这个接口需要适配
  • Adapter 对Adaptee的接口与Target接口进行适配

协作

Client在Adapter实例上调用一些操作。接着适配器调用Adaptee的操作实现这个请求。

适配器模式的实现

  • “对象”适配器 这个适配器模式充满着良好的OO设计原则:使用对象组合,以修改的接口包装被适配者:这种做法还有额外的优点,那就是,被适配者的任何子类,都可以搭配着适配器使用。
  • “类”适配器 “类”适配器需要多重继承才能够实现它,这在Java中是不可能的。但是当你在使用多重继承语言的时候,还是可能遇到这样的需求。 “对象”适配器 VS “类”适配器 “对象”适配器和“类”适配器使用两种不同的适配方式(分别是组合与继承)。“类”适配器继承了Target和Adaptee;而“对象”适配器利用组合的方式将请求传送给被适配者。 “类”适配器: a) 用一个具体的Adapter类对Adaptee和Target进行匹配。结果是当我们想要匹配一个类以及所有它的子类时,“类”适配器将不能胜任工作。 b) 是的Adapter可以重定义Adaptee的部分行为,因为Adapter是Adaptee的一个子类。 c) 仅仅引入了一个对象,并不需要额外的指针以间接得到adaptee。 “对象”适配器: a) 允许一个Adapter与多个Adaptee ———— 即Adaptee本身以及它的所有子类(如果有子类的话)一同工作。 b) 是的重定义Adaptee的行为比较困难。这就需要生成Adaptee的子类并且使得Adapter引用这个子类而不是Adaptee本身。
  • 智能适配器 在实际开发中,适配器也可以实现一些Adaptee没有实现,但是在Target中定义的功能,这种情况就需要在适配器的实现里面,加入新功能的实现,这种适配器被称为智能适配器。 如果要使用智能适配器,一般新加入的功能的实现,会用到很多Adaptee的功能,相当于利用Adaptee的功能来实现更高层的功能。当然也可以完全实现新加的功能,跟已有的功能都不靠边,变相是扩展了功能。
  • 适配多个Adaptee 适配器在适配的时候,可以适配多个Adaptee,也就是说实现某个新的Target的功能的时候,需要调用到多个模块的功能,适配多个模块的功能才能满足新接口的要求。
  • 缺省适配 缺省适配的意思是:为一个接口提供缺省实现。有了它,就不用直接去实现接口,而是采用继承这个缺省适配对象,从而让子类可以有选择的去覆盖实现需要的方法,对于不需要的方法,就使用缺省适配的方法就可以了。
  • 双向适配器 适配器也可以实现双向的适配,前面我们讲的都是把Adaptee适配成为Target,其实也可以把Target适配成为Adaptee,也就是说这个适配器可以同时当作Target和Adaptee来使用。在两个不同的客户需要用不同的方式查看同一个对象时,双向适配器尤其有用。

相关模式

  • 适配器模式 VS 装饰模式 适配器模式与装饰模式很类似,但仅仅是类似,造成这种类似的原因:两种设计模式在实现上都是使用的对象组合,都可以在转调组合对象的功能前后进行一些附加的处理,因此有这么一个相似性。它们的目的和本质都是不一样的。一般适配器适配是需要改变接口的;而装饰模式是不改接口的,无论多少层装饰都是一个接口。 装饰模式的本质是扩展包装的对象的行为或责任;而适配器模式本质是转换匹配,复用功能。
参考

《Head First 设计模式》 《设计模式:可复用面向对象软件的基础》 《研磨设计模式》

本文参与腾讯云自媒体分享计划,欢迎正在阅读的你也加入,一起分享。

发表于

我来说两句

0 条评论
登录 后参与评论

相关文章

来自专栏程序之美

spring bean的作用域

Bean的作用域 参考:spring FrameWork官方文档 spring4.x中官方有7中作用域,如果使用的是applicationContext作为...

782
来自专栏gaoqin31

设计模式之 工厂模式

简单工厂模式 : 简单工厂模式是属于创建型的设计模式,又叫做静态工厂方法模式,但不属于23种GOF设计模式,简单工厂模式是由一个工厂决定创建哪一类产品的实例,简...

1275
来自专栏用户画像

Spring中bean的作用域

1、singleton作用域 当一个bean的作用域设置为singleton, Spring IOC容器只会创建该bean定义...

542
来自专栏吴伟祥

spring为何要注入接口,而注入接口的实现类就会报错

  首先说明,注入的对象确实为实现类的对象。(并不是实现类的代理对象,注入并不涉及代理)

601
来自专栏向治洪

适配器模式

适配器模式(Adapter):将一个类的接口转换成客户希望的另外一个接口。adapter 模式使得原本由于接口不兼容而不能一起工作的那些类可以一起工作。 适...

1869
来自专栏轮子工厂

设计模式(二)之装饰模式 | 说好了面向对象,谁也不许赖谁~

开放封闭原则:软件应该可以扩展,但不可以修改。对于扩展是开放的,对于更改是封闭的。

551
来自专栏Java工程师日常干货

纯手写实现JDK动态代理前言JDK动态代理 手写代码实现JDK动态代理

在Java领域,动态代理应用非常广泛,特别是流行的Spring/MyBatis等框架。JDK本身是有实现动态代理技术的,不过要求被代理的类必须实现接口,不过cg...

752
来自专栏lgp20151222

判断微信用户是否关注了公众号

然后,我们为了获取他有没有关注我们公众号,要求他先授权登录获取token和openid,然后授权了之后查这个接口。

1013
来自专栏大闲人柴毛毛

Spring速查手册(二)——Bean的作用域

Bean的四种作用域 单例(Singleton):整个应用中,只创建一个bean。 原型(Prototype):每次注入或请求要给bean的时候都创建一个新的...

3228
来自专栏静默虚空的博客

JAVA 设计模式 适配器模式

用途 适配器模式 (Adapter) 将一个类的接口转换成客户希望的另外一个接口。 Adapter模式使得原本由于接口不兼容而不能一起工作的那些类可以一起工...

1818

扫码关注云+社区