第8章 适配器模式

合集下载
  1. 1、下载文档前请自行甄别文档内容的完整性,平台不提供额外的编辑、内容补充、找答案等附加服务。
  2. 2、"仅部分预览"的文档,不可在线预览部分如存在完整性等问题,可反馈申请退款(可完整预览的文档不适用该条件!)。
  3. 3、如文档侵犯您的权益,请联系客服反馈,我们会尽快为您处理(人工客服工作时间:9:00-18:30)。

// 适配器 public class Adapter implements ITarget { Adaptee adaptee = new Adaptee(); public void Request() { adaptee.SpecificRequest(); } } public class Client { public static void main(String[] args) { ITarget t = new Adapter(); t.Request(); } }
问题?
我们原来有一个程序使用鸭子对象,现在 想让它使用火鸡对象,但是火鸡与鸭子的 接口不同,不能直接使用。 写一个火鸡适配器,让火鸡看起来像鸭子
火鸡适配器
public class TurkeyAdapter implements Duck { Turkey turkey; public TurkeyAdapter(Turkey turkey) { this.turkey = turkey; } 火鸡适配器包装了一 public void quack() { 个火鸡对象,同时实 现了鸭子接口。这样 turkey.gobble(); 就可以像使用鸭子一 } 样使用火鸡了。 public void fly() { for(int i=0; i < 5; i++) { turkey.fly(); } } }
结构型模式简介 – 适配器模式(Adapter) – 桥接模式(Bridge) – 组合模式(Composite) – 装饰模式(Decorator) – 外观模式(Facade) – 享元模式(Flyweight) – 代理模式(Proxy)
Adapter(适配器)模式
“不合适的插座”
你的电脑的插头是三相的 而墙上的插座只有两相的 插头和插座的“接口”不匹配,怎么办?
ConcreteTarget + request () ... adaptee.specificRequest();
Adapter - adaptee : Adaptee - target : Target + request () + specificRequest () + setTarget (Target target) + setAdaptee (Adaptee adaptee) ...
对象适配器效果
① 允许一个Adapter与多个Adaptee及它们所
有子类同时工作。 Adapter 也可以一次给
所有的Adaptee添加功能 ② 使得重定义 Adaptee 的行为比较困难。这 就 需 要 生 成 Adaptee 的 子 类 并 且 使 得 Adapter引用这个子类而不是引用Adaptee 本身。
办法之一
New System
B
办法之二
System
A
B
Adapter
第二种方案的优点
System
Adapter
B
不需要修改代码
新代码
不需要修改代码
办法之三
System
B’
B
示 例
鸭子接口 public interface Duck { public void quack(); public void fly(); }
被适配者 Adaptee 类没有 Request方法,而客 户期待这个方法 为使客户能够使用 Adaptee 类,提供一个中 间环节,即类Adapter类
Adapter 类实现 Target 接口,继承 Adaptee ,
Adapter 的 Request 方法重新封装 Adaptee 的
第8章 适配器模式(Adapter)
2015-4-20
1
结构型模式
结构型模式概述 结构型模式描述如何将类或对象结合在
一起形成更大的结构
搭积木,可以通过简单积木的组合形成
复杂的、功能更为强大的结构
结构型模式
结构型模式分为类结构型模式和对象结构型模式: 类结构型模式关心类的组合,由多个类可以
鸭子接口Duck,定义 鸭子具有“鸣叫”和 “飞行”方法
MallardDuck类
public class MallardDuck implements Duck { public void quack() { System.out.println("嘎嘎嘎..."); } public void fly() { System.out.println("我在飞哦!"); } }
对象适配器模式(Object Adapter)结构
Client Target + request () ... Adaptee + specificRequest () ...
Adapter + request () ...
adaptee
adaptee.specificRequest();
客户端需要调用 Request 方法,而 Adaptee 没 有该方法,为了使客户端能够使用 Adaptee 类,需要提供类Adapter Adapter包装一个 Adaptee的实例,从而将客 户端与Adaptee衔接起来
MallardDuck类简单地 实现了Duck接口。
现在有一种新家伙
public interface Turkey { public void gobble(); public void fly(); }
WildTurkey
public class WildTurkey implements Turkey { public void gobble() { System.out.println("咕咕咕..."); } public void fly() { System.out.println("我在飞,不过飞不远"); } }
概念理解
适配器模式 把一个类的接口(被适配者)变换成客户端所期待的另一种 接口(目标),从而使原本因接口原因不匹配而无法一起 工作的两个类能够一起工作。
该模式中涉及有目标、被适配者和适配器。
适配器模式的关键是建立一个适配器,这个适 配器实现了目标接口并包含有被适配者的引用。
别名:包装器(Wrapper),变压器模式
使用适配器
public class DuckTestDrive { public static void main(String[] args) { MallardDuck duck = new MallardDuck(); WildTurkey turkey = new WildTurkey(); Duck turkeyAdapter = new TurkeyAdapter(turkey); System.out.println("火鸡说..."); turkey.gobble(); 在需要鸭子对象的 turkey.fly(); 地方使用了火鸡适 System.out.println("\n鸭子说..."); 配器对象, 火鸡适 testDuck(duck); 配器对象包装了一 System.out.println("\n火鸡适配器说..."); 个火鸡对象,所以 testDuck(turkeyAdapter); 实际使用的是火鸡 } 对象。 static void testDuck (Duck duck) { duck.quack(); duck.fly(); } } 需要使用鸭子对象
分 析
目标接口:鸭子接口
被适配者
适配器
客户 要使用鸭子 对象的程序
火鸡接口
把火鸡装 扮成鸭子
两者无耦合 彼此不必知道对方的存在
试试看
如果希望把鸭子包装成火鸡该怎么做? 写出你的代码DuckAdapter
DuckAdapter
import java.util.Random; public class DuckAdapter implements Turkey { Duck duck; Random rand; public DuckAdapter(Duck duck) { this.duck = duck; rand = new Random(); } public void gobble() { duck.quack(); } public void fly() { if (rand.nextInt(5) == 0) { duck.fly(); } } }
// 适配器 public class Adapter extends Adaptee implements ITarget { public void Request() { this.SpecificRequest(); } }
public class Client { public static void main(String[] args) { ITarget t = new Adapter(); t.Request(); } }
双向适配器
在对象适配器的使用过程中,如果在适配
器中同时包含对目标类和适配者类的引用 适配者可以通过它调用目标类中的方法, 目标类也可以通过它调用适配者类中的方 法,那么该适配器就是一个双向适配器。
双向适配器
Target + request () ...
target adaptee
Adaptee + specificRequest () ...
适配器模式的结构与使用
适配器模式的两种形式:
①类的适配器模式 ②对象的适配器模式
类的适配器模式(Class Adapter)结构
Client Target + request () ... Adaptee + specificRequest () ...
Adapter + request () ...
类适配器效果 ① 用 Adapter 类对 Adaptee 和 Target 进行匹配。
当想要匹配一个类以及所有它的子类时,
类Adapter将不能胜任工作 ② 使得Adapter可以重定义 Adaptee 的部分行 为,因为Adapter是Adaptee的一个子类。 ③ 仅仅引入一个对象,并不需要额外的指针 以间接得到adaptee
Adapter(适配器)模式 接口转换
请求 客户
转换后的请求
适配器
面向对象软件系统的适配问题 假设我们已经有一个软件系统,原来使用 了一个第三方类库A。现在有一个新的第三 方类库B,其功能等各方面都更加强大。 我们希望用 B来替换 A ,以改善我们的系统。 但是B的接口与A不一样。那怎么办呢?
SpecificRequest方法,实现适配的目的
//目标 public interface ITarget { // Methods void Request(); } //被适配者 public class Adaptee { // Methods public void SpecificRequest() { System.out.println("Called SpecificRequest()" ); } }
由于 Adapter与Adaptee是委派关系,这决定
了这个适配器模式是对象的
//目标 public interface ITarget { // Methods void Request(); }
//被适配者 public class Adaptee { public void SpecificRequest() // Methods { System.out.println("Called SpecificRequest()" ); } }
组合成一个更大的系统,在类结构型模式中
一般只存在继承关系和实现关系。
对象结构型模式关心类与对象的组合,通过
关联关系使得在一个类中定义另一个类的实
例对象,然后通过该对象调用其方法。
结构型模式
根据“合成复用原则”,在系统中尽量 使用组合关系来替代继承关系,因此大
部分结构型模式都是对象结构型模式。
结构型百度文库式
specificRequest();
客户Client
目标(Target) 客户所期待的接口
被适配者( Adaptee ):一个已经存在的、需
要适配的类,它具有Client要求的功能但不符
合Client的接口要求
适配器(Adapter)
对Adaptee的接口与Target接口进行适配
适配器模式的核心类
相关文档
最新文档