正文

一、定义

适配器模式将一个类的接口(被适配者),转换成客户期望的另一个接口。适配器让原本接口不兼容的类可以合作无间。

要点:

  • 适配器实现了目标接口,并持有被适配者的实例。
  • 适配器使用被适配者的方法,把请求转换成被适配者的一个或多个方法。
  • 客户通过目标接口调用适配器的方法对适配器发出请求。
  • 客户与被适配者是解耦的,一个不知道另一个。
  • 当需要使用一个现有的类而其接口并不符合你的需要时,就使用适配器。

二、实现步骤

1、创建被适配者接口

/**
* 被适配者接口
*/
public interface Adaptee { public void specificRequest();
}

2、创建具体的被适配者,并实现被适配者接口

/**
* 具体的被适配者
*/
public class ConcreteAdaptee implements Adaptee { @Override
public void specificRequest() {
System.out.println("ConcreteAdaptee is doing something...");
}
}

3、创建目标接口

/**
* 目标接口
*/
public interface Target { public void request();
}

4、创建适配器类,并实现目标接口

适配器持有被适配者,并在收到请求时调用被适配者的方法。

/**
* 适配器
*/
public class Adapter implements Target { /**
* 被适配者
*/
Adaptee adaptee; public Adapter(Adaptee adaptee) {
this.adaptee = adaptee;
} @Override
public void request() {
// 调用被适配者方法
adaptee.specificRequest();
}
}

5、使用适配器转换被适配者

public class Test {

    public static void main(String[] args) {
// 被适配者
Adaptee adaptee = new ConcreteAdaptee();
// 适配器
Adapter adapter = new Adapter(adaptee);
adapter.request();
}
}

三、举个栗子

1、背景

你上班的公司做了一套模拟鸭子游戏。现在,假设你缺鸭子对象,想用一些火鸡对象来冒充。

显而易见,因为火鸡的接口不同,所以我们不能公然拿来用。

2、实现

使用适配器把火鸡的方法转换成鸭子的方法,这样表面上看起来就像是一只鸭子了。

(1)创建火鸡接口

/**
* 火鸡接口(被适配者)
*/
public interface Turkey { /**
* 咯咯叫
*/
public void gobble(); /**
* 飞行
*/
public void fly();
}

(2)创建具体的火鸡

/**
* 野火鸡
*/
public class WildTurkey implements Turkey { @Override
public void gobble() {
System.out.println("Gobble gobble");
} @Override
public void fly() {
System.out.println("I'm flying a short distance");
}
}

(3)创建鸭子接口

/**
* 鸭子接口(目标接口)
*/
public interface Duck { /**
* 呱呱叫
*/
public void quark(); /**
* 飞行
*/
public void fly();
}

(4)创建火鸡适配器,并实现鸭子接口

/**
* 火鸡适配器
*/
public class TurkeyAdapter implements Duck { /**
* 火鸡
*/
Turkey turkey; public TurkeyAdapter(Turkey turkey) {
this.turkey = turkey;
} @Override
public void quark() {
turkey.gobble();
} @Override
public void fly() {
// 火鸡飞行距离比鸭子短,因此需要调用5次火鸡的fly()方法。
for (int i = 0; i < 5; i++) {
turkey.fly();
}
}
}

(5)使用火鸡适配器,将火鸡适配成鸭子

public class Test {

    public static void main(String[] args) {
// 火鸡(被适配者)
Turkey turkey = new WildTurkey();
// 火鸡适配器
TurkeyAdapter turkeyAdapter = new TurkeyAdapter(turkey);
turkeyAdapter.quark();
turkeyAdapter.fly();
}
}

《Head First 设计模式》:适配器模式的更多相关文章

  1. 20. 星际争霸之php设计模式--适配器模式

    题记==============================================================================本php设计模式专辑来源于博客(jymo ...

  2. Java设计模式——适配器模式

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

  3. linkin大话设计模式--适配器模式

    linkin大话设计模式--适配器模式 大家知道,在java中只允许单继承,但是在实际问题中往往都需要多继承,java引入了接口这一概念.(一个类可以实现多个接口) 由于接口中都是抽象方法,那么我们在 ...

  4. php设计模式适配器模式

    php设计模式适配器模式 简介 适配器模式(有时候也称包装样式或者包装)将一个类的接口适配成用户所期待的.一个适配允许通常因为接口不兼容而不能在一起工作的类工作在一起. 其实就是通过一个转换类,这个转 ...

  5. 【设计模式】Java设计模式 - 适配器模式

    [设计模式]Java设计模式 - 适配器模式 不断学习才是王道 继续踏上学习之路,学之分享笔记 总有一天我也能像各位大佬一样 原创作品,更多关注我CSDN: 一个有梦有戏的人 准备将博客园.CSDN一 ...

  6. [Head First设计模式]身边的设计模式——适配器模式

    系列文章 [Head First设计模式]山西面馆中的设计模式——装饰者模式 [Head First设计模式]山西面馆中的设计模式——观察者模式 [Head First设计模式]山西面馆中的设计模式— ...

  7. JAVA 设计模式 适配器模式

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

  8. Java设计模式 - 适配器模式

    概念: 将一个类的接口,转换成客户期望的另一个接口.适配器模式让原来接口不兼容的类可以在一起工作. 解决的问题: 提供类似于中间人的作用:把原本不兼容.不能一起工作的接口组合在一起,使得它们能够在一起 ...

  9. 24种设计模式--适配器模式【Adapter Pattern】

    今天讲适配器模式,这个模式也很简单,你笔记本上的那个拖在外面的黑盒子就是个适配器,一般你在中国能用,在日本也能用,虽然两个国家的的电源电压不同,中国是 220V,日本是 110V,但是这个适配器能够把 ...

  10. 结合JDK源码看设计模式——适配器模式

    定义: 将一个类的接口转换成客户期望的另外一个接口(重点理解适配的这两个字),使得接口不兼容的类可以一起工作适用场景: 已经存在的类,它的方法和需求不匹配的时候 在软件维护阶段考虑的设计模式 详解 首 ...

随机推荐

  1. Python如何向SQLServer存储二进制图片

    需求是需要用python往 SqlServer中的image类型字段中插入二进制图片 核心代码,研究好几个小时的代码: 安装pywin32,adodbapi image_url = "图片链 ...

  2. linux命令笔记记录(自用)

    1.解除yum锁定: sudo rm -rf /var/run/yum.pid 2.删除文件夹: rm -rf /var/log/httpd/access 3.更新pip: python -m pip ...

  3. Jarvisoj-web phpinfo

    题目入口:http://web.jarvisoj.com:32784/ 一进来就看到源码 简单分析之后知道考点是反序列化,注意到了关键字session_start(),这个函数是用于创建会话.但具体如 ...

  4. element上传功能携带参数

    在写element的上传功能时,需要对上传的文件携带参数,但是参数比较多,就需要一个对象合并的方法,Object.assign() Object.assign(target, source1, sou ...

  5. Python(set/list/dict/tuple)

    set集合:set是一个无序,不重复元素的集合.可嵌套列表,字典(可以for循环或者迭代的对象). ######差集: a={11,22} b={22,33} c=a.difference(b) #a ...

  6. Android:沉浸式状态栏(二)集成

    在Activity的onCreate()方法中添加代码 //设置状态栏透明 StatusBarUtil.setTranslucentStatus(this); //设置透明状态栏的paddingTop ...

  7. JVM系列之:String.intern的性能

    目录 简介 String.intern和G1字符串去重的区别 String.intern的性能 举个例子 简介 String对象有个特殊的StringTable字符串常量池,为了减少Heap中生成的字 ...

  8. PHP uasort() 函数

    ------------恢复内容开始------------ 实例 使用用户自定义的比较函数对数组 $arr 中的元素按键值进行排序: <?phpfunction my_sort($a,$b){ ...

  9. PHP restore_exception_handler() 函数

    定义和用法 restore_exception_handler() 函数恢复之前的异常处理程序. 该函数用于在通过 set_exception_handler() 函数改变后恢复之前的异常处理程序. ...

  10. P3565 由简单的树形dp 引入 长链刨分

    这道题感觉不太行 因为自己没想出来. 先说一下暴力吧,取三个点 让两两之间的距离相等怎么做呢,看起来是很复杂的样子的,但是仔细观察发现 答案出自一个点的儿子之间 或者儿子和父亲之间. 暴力枚举三个点然 ...