zoukankan      html  css  js  c++  java
  • 设计模式:适配器模式

    适配器模式  


    一、引子 
        昨天在给新买的MP3 充电的时候,发现这款MP3 播放器只提供了USB 接口充电的方式, 
    而它所配备的充电器无法直接给USB 接口充电,聪明的厂商为充电器装上了一个USB 接口转换 
    器解决了问题。 
        这个USB 接口转接器正是我们今天要谈到的适配器。而在软件开发中采用类似于上面方式 
    的编码技巧被称为适配器模式。 


    二、定义和结构 
         《设计模式》一书中是这样给适配器模式定义的:将一个类的接口转换成客户希望的另外 
    一个接口。Adapter  模式使得原本由于接口不兼容而不能一起工作的那些类可以一起工作。由 
    引子中给出的例子可知,这个定义描述的功能和现实中的适配器的功能是一致的。 
        可能你还是不太明白为什么要使用适配器模式。我们来举个例子也许能更直接的解除你的 
    疑惑。 
        比如,在一个画图的小程序中,你已经实现了绘制点、直线、方块等图形的功能。而且为 
    了让客户程序在使用的时候不用去关心它们的不同,还使用了一个抽象类来规范这些图形的接 
    口。现在你要来实现圆的绘制,这时你发现在系统其他的地方已经有了绘制圆的实现。在你庆 
    幸之余,发现系统中已有的方法和你在抽象类中规定的方法名称不一样!这可怎么办?修改绘 
    制圆的方法名,就要去修改所有使用它的地方;修改你的抽象类的方法名,也要去修改所有图 
    形的实现方法以及已有的引用。还有其它的方法没有?那就是适配器模式了。 
        可以看出使用适配器模式是为了在面向接口编程中更好的复用。如果你的系统中没有使用 
    到面向接口编程,没有使用到多态,我想大概也不会使用到适配器模式。 
        下面来看看适配器模式的组成吧。 
    1)  目标(Target)角色:定义Client 使用的接口。 
    2)  被适配(Adaptee)角色:这个角色有一个已存在并使用了的接口,而这个接口是需要我们 
        适配的。 
    3)  适配器(Adapter)角色:这个适配器模式的核心。它将被适配角色已有的接口转换为目标 
        角色希望的接口。 
        放上一个简单的类图,这只是适配器模式实现的一种情况: 


                                Adaptee 


                                 Target 


                                 Adapter 


    三、分类 
        在《设计模式》一书中将适配器模式分为类适配器模式和对象适配器模式。区别仅在于适 
    配器角色对于被适配角色的适配是通过继承完成的还是通过组合来完成的。由于在java 中不支 

    持多重继承,而且继承有破坏封装之嫌,众多的书中(包括《设计模式》)都提倡使用组合来代

    替继承。因此这里我们就不再对类适配器模式进行介绍(其实用的也很少)。 

        在上一小节的类图中描述的就是对象适配器模式。Adapter 对Adaptee  的转换是通过组合 
    来完成的(如果你还搞不懂类图中基本元素的含义,请先阅读我的《UML 类图介绍》)。 


    四、举例 
        接着上面举的画图程序的例子,先来看看在添加绘制圆的需求前的类结构: 


                              Shape 


                            Adaptee 


                Point          Line          Square              TextCircle 


        添加了圆的绘制以后的类结构: 


                        Shape                 Target 


                              Adaptee 


          Point          Line         Square         Circle            TextCircle 


                             Adapter 


        可以看出Shape、Circle 和TextCircle 三者的关系是和标准适配器模式中Target、Apater、 
    Apatee  三者的关系相对应的。我们只关心这个画图程序中是怎么来使用适配器模式的。看看 
    Circle 的实现代码吧: 


      class Circle extends Shape 
      { 
         //这里引用了TextCircle 
        private TextCircle tc; 
        public Circle () 
        { 
            tc= new TextCircle();  //初始化 
        } 
        void public display() 

        { 
           tc.displayIt();        //在规定的方法里面调用TextCircle 原来的方法 
        } 
      } 


        这样一个简单的适配器实现就完成了。 
        其实在适配器角色中不仅仅可以完成接口转换的过程,而且还可以对其功能进行改进和扩 
    充,当然这就不属于适配器模式描述的范围内了。 
        前面我介绍过了代理模式,两者的主要区别在于代理模式应用的情况是不改变接口命名的, 
    而且是对已有接口功能的一种控制;而适配器模式则强调接口转换。 


    五、题外话 
        在java  中有一种叫做“缺省适配模式”的应用,它和我们所讲的适配器模式是完全的两种东 
    西。缺省适配模式是为一个接口提供缺省的实现,这样子类型就可以从缺省适配模式中进行扩 
    展,避免了从原有接口中扩展时要实现一些自己不关心的接口。在java.awt.event中的 

    XXXAdapter 就是它的很好的例子,有兴趣的可以看看。 

    下载:

    http://download.csdn.net/detail/undoner/5335717

    深入浅出设计模式-中文版

  • 相关阅读:
    MySQL的图形化安装
    java笔记整理
    运动会报名系统的简易实现
    JDBC知识点总结
    MySQL常用知识总结
    python的传参数用法
    R统计数据框的行数
    SAINT学习笔记
    win10 双网卡设置内网和外网同时访问
    根据GSVA结果绘制不同组的趋势图
  • 原文地址:https://www.cnblogs.com/wuyida/p/6301023.html
Copyright © 2011-2022 走看看