设计模式-适配器模式
介绍
-
将某个类的接口转换成客户端期望的另一接口表示,目的主要是兼容性,让另个不能在一起工作的另个类可以协同工作
-
适配者与被适配者的关系是解耦的,是通过中间的适配类实现(有种类似两表中间的关系表)
类适配器
就是将接口(200),转换成自己所需要的(5v)
uml类图
适配器类,通过实现接口,继承被适配者。使用者仅需依赖接口即可。
代码实现
被适配者
/**
* @program: learn_day01
* @description: 被适配者
* @author: wfg
* @create: 2021-05-07 18:12
*/
public class Voltage {
/**
* @Description: 220负电压
* @Author: wfg
*/
int src = 220;
/**
* @Description: 方法输出220
* @Author: wfg
*/
public int outPut(){
return src;
}
}
适配器接口
/**
* @program: learn_day01
* @description: 适配接口 输出5v接口
* @author: wfg
* @create: 2021-05-07 18:24
*/
public interface IVoltage5 {
/**
* @Description: 定义5v接口
* @Author: wfg
*/
public int outVol5();
}
适配器类(需要继承被适配器类)
/**
* @program: learn_day01
* @description: 适配器类 通过实现5v接口,与继承220v 类,通过一定逻辑将220v转换成5v
* @author: wfg
* @create: 2021-05-07 18:26
*/
public class VoltageAdapter extends Voltage implements IVoltage5{
/**
* @Description: 类适配器,通过依赖其voltage进行逻辑操作
* @Author: wfg
*/
public Voltage voltage;
@Override
public int outVol5() {
int src = outPut();
int zhSrc= src/44;
return zhSrc;
}
}
}
使用者仅需要依赖适配器接口
/**
* @program: learn_day01
* @description: 手机需要5v电压
* @author: wfg
* @create: 2021-05-07 18:32
*/
public class Phone {
public Phone(IVoltage5 iVoltage5){
System.out.println(iVoltage5.outVol5());
}
}
**缺点:**由于适配器类,需要继承被适配器类并调用里面方法,使得被适配器类的方法暴露,增加了使用成本
对象适配器
根据合成服用原则(使用关联关系来替代继承关系),因此对象适配器类和类适配器模式相同,只是将适配器类与被适配器类继承关系改成依赖关系,对象适配器类模式是适配器类最常用的一种
uml类图
对象适配器类只是将继承关系改成了依赖的关系(可以在构造器/set方法里赋值)
代码实现
被适配者
/**
* @program: learn_day01
* @description: 被适配者
* @author: wfg
* @create: 2021-05-07 18:12
*/
public class Voltage {
/**
* @Description: 220负电压
* @Author: wfg
*/
int src = 220;
/**
* @Description: 方法输出220
* @Author: wfg
*/
public int outPut(){
return src;
}
}
适配器类(主要的改变就是从继承,编成了聚合方式)
/**
* @program: learn_day01
* @description: 对象适配器类 通过实现5v接口,依赖220v 类,通过一定逻辑将220v转换成5v
* @author: wfg
* @create: 2021-05-07 18:26
*/
public class VoltageAdapter implements IVoltage5{
/**
* @Description: 对象适配器,通过依赖其voltage进行逻辑操作
* @Author: wfg
*/
private Voltage voltage;
/**
* @Description: 通过构造器,使用聚合方式,关联棋类
* @Author: wfg
*/
public VoltageAdapter(Voltage voltage1){
voltage = voltage1;
}
@Override
public int outVol5() {
//注意null在前面·
if(null != voltage) {
int src = voltage.outPut();
int zhSrc = src / 44;
return zhSrc;
}
return 0;
}
}
** 使用方式同上**
注意事项:对象适配器与类适配器本质上是一种思想(将接口变成我们所需要的),只不过是实现方式不同。
接口适配器
介绍
当我们不需要实现接口提供的所有方法是,可以设计一个抽象类,实现接口,并为接口中每个方法提供默认实现的方法,这样该抽象类可有选择的覆盖某些方法实现需求
适用于:一个接口不想使用其所有方法的情况
注意:这里并没有违反接口隔离原则(因为实现接口的是抽象类,默认实现了所有方法),也没有违反里氏替换原则(这里由于并没有使用父类,所以可以重写方法(父类出现的地方替换子类))
uml类图
注意这里实现抽象类的话,就可以使用匿名内部类啦
代码实现
接口适配器
/**
* @program: learn_day01
* @description: 接口示配器
* @author: wfg
* @create: 2021-05-07 18:24
*/
public interface IVoltage5 {
/**
* @Description: 定义5v接口
* @Author: wfg
*/
public int outVol5();
/**
* @Description: 隨便加的
* @Author: wfg
*/
public int t1();
/**
* @Description: 隨便加的
* @Author: wfg
*/
public int t2();
}
抽象类
/**
* @program: learn_day01
* @description: 使用抽象類,來空實現接口所有方法
* @author: wfg
* @create: 2021-05-07 21:58
*/
public abstract class AbstarcVoltage implements IVoltage5{
//默認實現
@Override
public int t1() {
return 0;
}
@Override
public int outVol5() {
return 0;
}
@Override
public int t2() {
return 0;
}
}
使用方法(匿名内部类也太棒了吧)
/**
* @program: learn_day01
* @description: 使用匿名內部類實現
* @author: wfg
* @create: 2021-05-07 18:33
*/
public class Test {
public static void main(String[] args) {
//注意:這裡是重寫了抽象類
new AbstarcVoltage(){
@Override
public int outVol5() {
System.out.println("使用了匿名內部類");
return super.outVol5();
}
}.outVol5();
}
}