第七章:适配器模式
一、适配器概述
1)适配器模式(Adapter)可以帮助某个类转换成使用者期望的另一个接口表示(这段话不好理解,看下面的例子就理解了),别名又叫包装器(Wrapper)
2)适配器模式属于结构型模式,分为三类:类适配器模式、对象适配器模式、接口适配器模式
二、类适配器模式
1. 类适配器模式实例
现有一手机需要使用 5v 的接口充电,但是现在只提供 220v 的电源,所以我们就需要一个适配器。类图如下:
Voltage220 类
public class Voltage220 {
public int output220() {
return 220;
}
}
Voltage5 接口
public interface Voltage5 {
int output5();
}
VoltageAdapter 类
public class VoltageAdapter extends Voltage220 implements Voltage5 {
@Override
public int output5() {
int v = output220();
return v / 44;
}
}
Phone 类
public class Phone {
public void charge(Voltage5 source) {
int v = source.output5();
if (v == 5) {
System.out.println("正在充电");
} else {
System.out.println("充电异常");
}
}
}
测试类
public class AdapterTest {
public static void main(String[] args) {
Phone phone = new Phone();
phone.charge(new VoltageAdapter());
}
}
使用者去找适配器,适配器再去找被适配者,这样使用者就完成了使用被适配者的目的
2. 类适配器注意事项
1)因为 Java 是单继承,所以适配器继承 src(被适配者)类就使得 dst(适配目标)就必须是接口
2)src 类的方法在适配器类中都会暴露出来,增加了使用成本
3)由于适配器类继承了 src 类,所以它可以根据需求重写 src 类中的方法,增加了灵活性
三、对象适配器模式
1. 对象适配器模式举例
根据合成复用原则,应该少用继承多用聚合和组成,所以我们将刚刚的继承 src 类,变成聚合一个 src 对象,故称之为对象适配器模式
类图如下:
VoltageAdapter 类
public class VoltageAdapter implements Voltage5 {
private Voltage220 v220;
public VoltageAdapter() {
v220 = new Voltage220();
}
@Override
public int output5() {
int v = v220.output220();
return v / 44;
}
}
其他类同上不用动
2. 对象适配器注意事项
1)没有类适配器必须继承 src 类而带来的局限性
2)使用成本更低,更灵活
四、接口适配器模式
接口适配器模式顾名思义就是是配一个接口,它有点和上面不一样。它的作用是:当有一个接口,它有很多方法。现在我们想要使用这个接口中的某些方法,不得已必须实现其中的所有方法,即使是对用不到的方法做空实现也是一件很麻烦又占地方的事。所有就有了接口适配器,用它来对接口做空实现,然后我们再继承它,有选择的重写所需方法
1. 接口适配器模式举例
有很多方法的接口
public interface ManyFunctions {
void function1();
void function2();
void function3();
void function4();
void function5();
}
实现接口的抽象类
public abstract class InterfaceAdapter implements ManyFunctions {
@Override
public void function1() {
}
@Override
public void function2() {
}
@Override
public void function3() {
}
@Override
public void function4() {
}
@Override
public void function5() {
}
}
测试类
public class AdapterTest {
public static void main(String[] args) {
InterfaceAdapter hello = new InterfaceAdapter() {
@Override
public void function1() {
System.out.println("hello world");
}
};
hello.function1();
}
}