适配器模式

设计模式之适配器(Adapter Pattern)

定义:是两个不兼容的接口之间的桥梁。这种类型的设计模式属于结构型模式,它结合了两个独立接口的功能。

在生活中的案例

泰国中的插座是两孔的(欧标),可以使用多功能转接头(适配器),这样就可以使用了

如何使用?

适配器模式通过定义一个新的接口(对要实现的功能加以抽象),和一个实现该接口的Adapter(适配器)类来透明地调用外部组件。这样替换外部组件时,最多只要修改几个Adapter类就可以了。

适配器的形式:一种是类的适配器,一种是对象的适配器,一种是接口适配器。

适配器的原理:

  1. 将一个类的接口转换成另一种接口,让原本不兼容的类可以兼容。
    2.从用户的角度看不到被适配,是解耦合。
    3.用户调用适配器转化出来的目标接口方法,适配器在被适配者的相关接口方法。
    4.用户收到的反馈结果,感觉只是和目标接口交互。

如何进行实现?

继承或者依赖。

优点:

  • 1.可以让两个没有关联的类在一起运行。
  • 2.提高类的复用性
  • 3.增加类的透明度。
  • 4.灵活性更好。

缺点:

  • 1、过多地使用适配器,会让系统非常零乱,不易整体进行把握。比如,明明看到调用的是 A 接口,其实内部被适配成了 B 接口的实现,一个系统如果太多出现这种情况,无异于一场灾难。因此如果不是很有必要,可以不使用适配器,而是直接对系统进行重构。
  • 2.由于 JAVA 至多继承一个类,所以至多只能适配一个适配者类,而且目标类必须是抽象类。

类的适配器:

由三种角色组成:

  • 1.源角色:现在需要适配的接口
  • 2.目标角色:所期待得到的接口
  • 3.适配器角色:这是本模式的核心。适配器接口将源接口转成目标接口。
    需求:原来有一个充电器,可以给手机充电,但是现在需要还能给耳机充电
    源角色:
/**
 * 充电器接口
 */
public interface ICharge {
    void charge();
}


/**
 * 苹果手机充电器需要适配的角色(Adapee)
 */
public class AppleCharger implements ICharge{
    public void charge(){
          System.out.println("The ApplePhone is charging ...");
    }
}

适配器角色

/**
  * 要对这个特殊的充电器进行适配,适配器接口(Target角色)
  */
 public interface IChargeAdapter {
     void charge();
 }

目标角色:

/**
 * 多接头充电器,支持一边充手机,一边充耳机(Adaper)
 */
public class MultipleJointsCharger extends AppleCharger implements IChargeAdapter{
    @Override
    public void charge() {
        super.charge();
        System.out.println("The Headset is charging ...");
    }
}

测试方法:

/**
 * 启动类
 */
@SpringBootApplication
public class StartClass {
    public static void main(String[] args){
        MultipleJointsCharger multipleJointsCharger = new MultipleJointsCharger();
        multipleJointsCharger.charge();
    }
}

结果为:

类适配器的缺点:

1.java是单继承机制,所以类适配器需要继承src类这一点算是一个缺点,因为这要求dst必须是接口,有一定的局限性。
2.src类的方法在Adapter中都会暴露出来,也增加了使用的成本
3.由于其继承了src类,所以它可以根据需求重写src类的方法,使得adapter的灵活性增强。

对象适配器

对象适配器基本介绍

1.基本思路和类的适配器模式相同,只是将Adapter类作修改,不是继承src类,而是持有src类的实例,以解决兼容性的问题。即:持有src类,实现dst类接口,完成src-》dst的适配。
2.根据“合成复用原则”,在系统中尽量使用关联关系来替代继承关系。
3.对象适配器模式是适配器模式常用的一种。

需求:苹果充电器,给苹果充电,安卓充电线给安卓充电,万能充电器,给两种手机充电。

/**
 * 充电器接口
 */
public interface ICharge {
    void charge();
}

/**
 * 安卓手机充电器需要适配的角色(Adaptee)
 */
public class AndroidCharger implements ICharge{
    @Override
    public void charge() {
        System.out.println("The AndroidPhone is charging ...");
    }
}

/**
 * 苹果手机充电器需要适配的角色(Adaptee)
 */
public class AppleCharger implements ICharge{
    public void charge(){
          System.out.println("The ApplePhone is charging ...");
    }
}

现在是万能充电器

 /**
  * 要对这个特殊的充电器进行适配,适配器接口(Target角色)
  */
 public interface IChargeAdapter {
     void charge();
 }

创建适配器实现类:

/**
 * 万能充电器,类的适配器(Adaper)
 */
public class UniversalCharger implements IChargeAdapter{
    private ICharge charge;

    public UniversalCharger(ICharge charge){
        this.charge = charge;
    }

    @Override
    public void charge() {
        charge.charge();
    }
}

测试类:

/**
 * 启动类
 */
@SpringBootApplication
public class StartClass {
    public static void main(String[] args){
        UniversalCharger universalCharger = new UniversalCharger(new AppleCharger());
        universalCharger.charge();

        UniversalCharger universalCharger1 = new UniversalCharger(new AndroidCharger());
        universalCharger1.charge();
    }
}

  • (1)类的适配器模式:当希望将一个类转换成满足另一个新接口的类时,可以使用类的适配器模式,创建一个新类,继承原有的类,实现新的接口即可。

  • (2)对象的适配器模式:当希望将一个对象转换成满足另一个新接口的对象时,可以创建一个包装类,持有原类的一个实例,在包装类的方法中,调用实例的方法就行。

posted @ 2021-07-26 09:28  King-DA  阅读(67)  评论(0)    收藏  举报