首页 > 其他分享 >适配器模式

适配器模式

时间:2023-01-02 16:24:09浏览次数:37  
标签:return 适配器 Tractor 模式 接口 public tractor

概述

《设计模式》一书中对 “适配器模式” 的动机描述如下:

将一个类的接口转换成客户希望的另一个接口,适配器模式使得原本由于接口不兼容而不能一起工作的类可以一起工作

一般情况下的类结构图如下所示:

Adapter.png

每个组件的介绍如下:

  • Client:实际调用目标接口的对象
  • Target:当前设计的用于客户端调用的接口类型
  • Adaptee:已经存在的类,但是和 Target 需要的接口不同
  • Adapter:组合 Adaptee,重写 Target 中定义的接口,使得 Adapter 能够使用 Adaptee 来完成 Target 需要的功能

一般在以下几种情况中会考虑使用适配器模式:

  • 希望使用一个已经存在的类,但是它的接口不符合目前的要求
  • 希望创建一个可以复用的类,该类可以与其他不相关的类或不可预见的类协同工作
  • 希望使用一些已经存在的子类,但是不可能对每一个都进行子类化以匹配它们的接口,在这种情况下可以使得 Adpater 适配这些子类的公有接口

具体实例

假设现在我们的系统现在需要创建有关交通工具的使用情况统计,我们需要一个如下的类型:

public interface Transportation {
    String name(); // 交通工具名称
    int walkType(); // 行走方式,空中、陆地、水
    double costForYear(); // 每年的消耗金额
}

假设我们的系统已经通过该接口完成了对应的统计需求,现在需要具体化相关的子类。比如,如果我们需要统计飞机的使用情况,那么可以定义相关的飞机子类:

public class Airplane implements Transportation {
    @Override
    public String name() {
        return "airplane";
    }
    
    @Override
    public int walkType() {
        return 0;
    }
    
    @Override
    public double costForYear() {
        return 350000.00;
    }
}

然而,现在已有的系统中已经存在了名为 Tractor 的交通工具,但是它的定义如下:

import java.math.BigDecimal;

public class Tractor {
    public String type() {
        return "tractor";
    }
    
    public BigDecimal costForDay() { // 拖拉机每天的消耗金额
        return BigDecimal.valueOf(15);
    }
    
    public int dayOfYear() { // 拖拉机一年的工作天数
        return 200;
    }
}

显然,现在系统中存在的 Tractor 无法与我们实现的交通工具统计协作,因为它不是 Transportation 类型的交通工具。一种方式是找到 Tractor 的源代码,强制其实现 Transportation 接口以符合当下系统的需求,但是这并不是合理的解决方案,因为在实际使用中,很大概率无法直接修改源代码。为此,我们可以创建一个适配器类 TractorTransportationAdapter,以协调两者之间的关系:

public class TractorTransportationAdapter implements Transportation {
    
    private final Tractor tractor;
    
    public TractorTransportationAdapter(Tractor tractor) {
        this.tractor = tractor;
    }
    
    @Override
    public String name() {
        return tractor.type();
    }
    
    @Override
    public int walkType() {
        return 1;
    }
    
    @Override
    public double costForYear() {
        return BigDecimal.valueOf(tractor.dayOfYear())
            .multiply(tractor.costForDay() == null ? BigDecimal.valueOf(0) : tractor.costForDay())
            .doubleValue();
    }
}

对于 ”统计交通工具“ 部分的逻辑来讲,现在只需要将 TractorTransportationAdapter 替换现有的 Tractor 作为对应的角色即可使得两者之间能够协同工作


参考:

[1] 《设计模式—可复用面向对象基础》

标签:return,适配器,Tractor,模式,接口,public,tractor
From: https://www.cnblogs.com/FatalFlower/p/17020047.html

相关文章

  • 笔记本 AUTO模式是什么意思
    相关文章电脑AUTO是什么意思https://zhidao.baidu.com/question/1645428036244428940.html##简介电脑屏幕、显示器上的按键“AUTO”是用来自动校对屏幕显示的位置的按......
  • python设计模式
    设计模式设计模式中使用了一个接口类abc:AbstractBaseClasses作用:在代码中定义和使用抽象基类进行API检查。​为什么使用abc模块Abstractbaseclasses由一组接口组......
  • redis单节点与集群模式
    23.redis实战Dockerfileroot@k8s-master1:~/k8s-data/dockerfile/web/magedu/redis#catDockerfile#RedisImageFROMharbor.nbrhce.com/baseimages/centos:7.9.20......
  • 基于 Dojo toolkit 实现 web2.0 的 MVC 模式
    前言MVC模式是设计模式中的经典模式,它可以有效的分离数据层,展示层,和业务逻辑层。Web2.0技术由于其良好的用户体验被广泛应用于WEB应用的展示层。但是在传统的web开发......
  • 使用Qt和Interpreter设计模式开发计算器(附源码)
    计算器软件其实有很多种,但是基本上都是模仿计算器,用鼠标点击按键来操作,这次我们反其道而行之,采用类似文本输入的操作方式。功能1.键盘输入算式,回车后计算结果。2.根据当前......
  • KMP字符串模式匹配详解
    KMP字符串模式匹配详解KMP字符串模式匹配通俗点说就是一种在一个字符串中定位另一个串的高效算法。简单匹配算法的时间复杂度为O(m*n);KMP匹配算法。可以证明它的时间复杂度......
  • 单例模式
    概述《设计模式》一书中对单例模式的“动机”描述如下:保证一个额类仅有一个实例,并提供一个访问它的全局访问点一般情况下,为了避免资源的浪费,可以考虑将一些不可变类......
  • BigDecimal 舍入模式(Rounding mode)中的ROUND_UNNECESSARY
    BigDecimal.ROUND_UNNECESSARY翻译:舍入模式可以断言所请求的操作具有准确的结果,因此不需要舍入。如果在产生不精确结果的操作上指定了这种舍入模式,则会引发ArithmeticExcept......
  • 光猫两种模式
    光猫光猫的两种模式路由模式​ 路由模式安装简单,但性能弱,在线设备过多,就会出现网络缓慢的情况,这也是大部分人家里的光猫模式。桥接模式​ 桥接模式,由于拨号......
  • 【Azure Developer】开发模式下使用AAD账号访问Azure Blob的相关参考
    问题描述开发模式下使用AAD账号访问AzureBlob的流程参考文件 问题解答第一步:先在AAD中注册一个APP,步骤可参考:将应用程序注册到Microsoft标识平台:​​https://docs.azur......