适配器模式

参考文章:《设计模式之美》——王争

一、概述

适配器模式Adapter Design Pattern),主要用来做适配的,它将不兼容的接口转换为可兼容的接口,让原本由于接口不兼容而不能一起工作的类可以一起工作,类似于“绿联”转接器。


二、实现方式

一种是基于继承关系实现,一种是基于组合关系实现。

一个完整的适配器模式主要包含三个角色:MyTarget、MyAdaptee和Adaptor

/**
 * 目标接口定义:需要进行适配的接口
 */
public interface MyTarget {
    void funtion1(); //方法
    void funtion2();
}

/**
 * 受改造者:需要将其改造以适配 MyTarget(目标接口)
 */
@Slf4j
public class MyAdaptee {
    public void functionA() {
        log.info("执行Adaptee的方法A");
    }
    public void functionB() {
        log.info("执行Adaptee的方法B");
    }
}

2.1 基于继承关系实现

/**
 * 适配器:类似防腐层,将 MyAdaptee 适配 MyTarget
 * 这样就能保证在现有的接口 MyTarget不变的情况下,新增入类 MyAdaptee
 * 基于继承关系实现:适用于 MyAdaptee方法不多,且与MyTarget接口定义大部分相同
 */
@Slf4j
public class Adaptor extends MyAdaptee implements MyTarget {

    @Override
    public void funtion1() {
        log.info("执行目标接口的function1");
        super.functionA();
    }

    @Override
    public void funtion2() {
        log.info("执行目标接口的function2");
        super.functionB();
    }
}

2.2 基于组合关系实现

/**
 * 适配器:类似防腐层,将 MyAdaptee 适配 MyTarget
 * 这样就能保证在现有的接口 MyTarget不变的情况下,新增入类 MyAdaptee
 * 基于组合关系实现:适用于 MyAdaptee方法很多,且与MyTarget接口定义有很多不同
 */
@Slf4j
public class Adaptor2 implements MyTarget {

    /**
     * 组合
     */
    private MyAdaptee adaptee;

    public Adaptor2(MyAdaptee adaptee) {
        this.adaptee = adaptee;
    }

    @Override
    public void funtion1() {
        log.info("执行目标接口的function1");
        adaptee.functionA();
    }

    @Override
    public void funtion2() {
        log.info("执行目标接口的function2");
        adaptee.functionB();
    }
}

三、适用场景

3.1 封装有缺陷的接口

外部有缺陷接口或类就是MyAdaptee,我们自己的重构接口就是MyTarget,以此进行重组。

3.2 统一多个类的接口设计

比如我们有多个过滤类(MyAdaptee),可以统一到一个重构接口MyTarget中。

  1. 两个MyAdaptee

    /**
     * A过滤方式
     */
    @Slf4j
    public class FilterAdapteeA {
        public void filteWord(String word) {
            log.info("A方式过滤词汇:{}", word);
        }
    }
    
    /**
     * A过滤方式
     */
    @Slf4j
    public class FilterAdapteeB {
        public void filteWord(String word) {
            log.info("B方式过滤词汇:{}", word);
        }
    }
    
  2. 两个MyTarget

    /**
     * 过滤器
     */
    public interface FilterTarget {
    
        /**
         * 过滤操作
         */
        void filteHandler(String word);
    }
    
    /**
     * 过滤适配器A
     */
    public class FilterAdaptorA implements FilterTarget {
    
        private FilterAdapteeA adapteeA;
    
        public FilterAdaptorA(FilterAdapteeA adapteeA) {
            this.adapteeA = adapteeA;
        }
    
        @Override
        public void filteHandler(String word) {
            adapteeA.filteWord(word);
        }
    }
    
    /**
     * 过滤适配器A
     */
    public class FilterAdaptorB implements FilterTarget {
    
        private FilterAdapteeB adapteeB;
    
        public FilterAdaptorB(FilterAdapteeB adapteeB) {
            this.adapteeB = adapteeB;
        }
    
        @Override
        public void filteHandler(String word) {
            adapteeB.filteWord(word);
        }
    }
    
  3. 管理类

    /**
     * 过滤管理
     */
    public class FilterManager {
    
        private List<FilterTarget> targets = Lists.newArrayList();
    
        /**
         * 添加过滤器
         */
        public void addFilter(FilterTarget target) {
            targets.add(target);
        }
    
        /**
         * 执行过滤
         */
        public void doFilter(String word) {
            targets.forEach(f -> f.filteHandler(word));
        }
    }
    

3.3 替换依赖的外部系统

自己创建一个MyAdaptee,实现外部接口(MyTarget)同时,将自己创建的类组合或继承,这样替换原有接口内的逻辑。

3.4 其他

兼容老版本接口、适配不同数据格式、Log4j与slf4j

评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值