适配器模式(别名:包装类) 将一个类的接口转换成客户希望的另外一个接口。Adapter模式使得原本由于接口不兼容而不能一起工作的那些类可以一起工作。
Adapter Pattern(Another Name: wrapper) Convert the interface of a class into another interface clients expect. Adapter lets classes work together that couldn’t otherwise because of incompatible interface.
类图
模式的结构与使用 由于Java不支持多重继承,即一个类只能有一个父类,所以本节给出适配器模式的类图按着GOF著作的分类属于对象适配器模式的类图,不是类适配器模式的类图。 对象适配器模式的结构中包括三个角色。
目标(Target):目标是一个接口,该接口是客户想使用的接口。
被适配者(Adaptee):被适配者是一个已经存在的接口或抽象类,这个接口或抽象类需要适配。
适配器(Adapter):适配器是一个类,该类实现了目标接口并包含有被适配者的引用,即适配器的职责是对被适配者接口或是抽象类于目标接口进行适配。
简单的例子 Target的抽象类ThreeElectricOutlet.java 1
2
3
4
5
package Adapter;
public interface ThreeElectricOutlet {
public abstract void connectElectricCurrent () ;
}
Adaptee的接口类TwoElectriOutlet.java 1
2
3
4
5
package Adapter;
public interface TwoElectricOutlet {
public abstract void connectElectricCurrent () ;
}
Adapter的实现类ThreeElectricAdapter.java 1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
package Adapter;
public class ThreeElectricAdapter implements ThreeElectricOutlet {
TwoElectricOutlet outlet;
public ThreeElectricAdapter (TwoElectricOutlet outlet) {
this .outlet = outlet;
}
@Override
public void connectElectricCurrent () {
outlet.connectElectricCurrent();
}
}
测试类Application.java 1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
39
40
41
42
43
44
45
46
47
48
49
50
51
52
53
54
55
56
57
58
59
60
package Adapter;
public class Application {
public static void main (String[] args) {
ThreeElectricOutlet outlet;
Wash wash = new Wash();
outlet = wash;
System.out.println("使用三相插座接通电源:" );
outlet.connectElectricCurrent();
TV tv = new TV();
ThreeElectricAdapter adapter = new ThreeElectricAdapter(tv);
outlet = adapter;
System.out.println("使用三相插座接通电源:" );
outlet.connectElectricCurrent();
}
}
class Wash implements ThreeElectricOutlet {
String name;
public Wash () {
name = "黄河洗衣机" ;
}
public Wash (String s) {
name = s;
}
@Override
public void connectElectricCurrent () {
turnOn();
}
private void turnOn () {
System.out.println(name + "开始洗衣服" );
}
}
class TV implements TwoElectricOutlet {
String name;
public TV () {
name = "长江电视机" ;
}
public TV (String s) {
name = s;
}
@Override
public void connectElectricCurrent () {
turnOn();
}
private void turnOn () {
System.out.println(name + "开始放节目" );
}
}
适配器的适配程度 1.完全适配 如果目标(Target)接口中的方法数目与配适配者(Adaptee)接口的方法数目相等,那么适配器(Adapter)可将被适配者接口(抽象类)与目标接口进行完全适配。
2.不完全匹配 如果目标(Target)接口中的方法数目少于配适配者(Adaptee)接口的方法数目,那么适配器只能将被适配者接口与目标接口进行部分适配。
3.剩余适配 如果目标(Target)接口中的方法数目大于配适配者(Adaptee)接口的方法数目,那么适配器(Adapter)可将被适配者接口(抽象类)与目标接口进行完全适配,但必须将目标多余的方法给出用户允许的默认实现。
适配器模式的优点
目标(Target)和被适配者(Adaptee)是完全解耦的关系。
适配器模式满足“开-闭原则”。当添加一个实现Adaptee接口的新类时,不必修改Adapter,Adapter就能对这个新类的实例进行适配。
试用适配器模式的情景
用户需要一个类的子类的实例,但不希望与该类的子类形成耦合。
用户需要一个类的子类的实例,但用户不知道该类有哪些子类可用。
下载源码请到 MyGitHub