zoukankan      html  css  js  c++  java
  • 10.java设计模式之外观模式

    基本需求

    • 组建一个家庭影院:DVD 播放器、投影仪、自动屏幕、环绕立体声、爆米花机,要求完成使用家庭影院的功能,
    • 其过程为:直接用遥控器:统筹各设备开关
    • 开爆米花机、放下屏幕、开投影仪、开音响、开 DVD,选 dvd、去拿爆米花、调暗灯光、播放、观影结束后,关闭各种设备

    传统方案

    • 客户端直接依赖各种设备,直接调用各种设备的方法
    • UML类图
    • 在Client中,创建各个子系统的对象,并直接去调用子系统(对象)相关方法,会造成调用过程混乱,没有清晰的过程,不利于维护
    • 定义一个高层接口,给子系统中的一组接口提供一个一致的界面(比如在高层接口提供四个方法ready, play, pause, end),用来访问子系统中的一群接口,就是通过定义一个一致的接口(界面类),用以屏蔽内部子系统的细节,使得调用端只需跟这个接口发生调用,而无需关心这个子系统的内部细节 -> 外观模式

    基本介绍

    • 外观模式(Facade)隐藏系统的复杂性,并向客户端提供了一个客户端可以访问系统的接口。这种类型的设计模式属于结构型模式,它向现有的系统添加一个接口,来隐藏系统的复杂性。这种模式涉及到一个单一的类,该类提供了客户端请求的简化方法和对现有系统类方法的委托调用

    • 为子系统中的一组接口提供一个一致的界面,外观模式定义了一个高层接口,这个接口使得这一子系统更加容易使用

    • 主要解决:降低访问复杂系统的内部子系统时的复杂度,简化客户端与之的接口

    • UMl类图(原理)

      • Facade类为外观类,聚合了其他多个子系统(实际功能的提供者),让client统一调用
    • UML类图(案例)

    • 代码实现

      • public class DVDPlayer {
        
           // DVD播放器 使用饿汉
           public static final DVDPlayer DVD_PLAYER = new DVDPlayer();
        
           private DVDPlayer() {
           }
        
           public static DVDPlayer getInstance() {
               return DVD_PLAYER;
           }
        
           public void on() {
               System.out.println("dvd on");
           }
        
           public void off() {
               System.out.println("dvd off");
           }
        
           public void play() {
               System.out.println("dvd play");
           }
        
           public void pause() {
               System.out.println("dvd pause");
           }
        
        }
        
      • public class Screen {
        
           // 屏幕 使用饿汉
           public static final Screen SCREEN = new Screen();
        
           private Screen() {
           }
        
           public static Screen getInstance() {
               return SCREEN;
           }
        
           public void up() {
               System.out.println("screen up");
           }
        
           public void dowm() {
               System.out.println("screen down");
           }
        
        }
        
        
      • public class Popcorn {
        
           // 爆米花机 使用饿汉
           public static final Popcorn POPCORN = new Popcorn();
        
           private Popcorn() {
           }
        
           public static Popcorn getInstance() {
               return POPCORN;
           }
        
           public void on() {
               System.out.println("popcorn on");
           }
        
           public void off() {
               System.out.println("popcorn off");
           }
        
           public void pop() {
               System.out.println("popcorn pop");
           }
        
        }
        
        
      • public class Projector {
        
           // 投影仪 使用饿汉
           public static final Projector PROJECTOR = new Projector();
        
           private Projector() {
           }
        
           public static Projector getInstance() {
               return PROJECTOR;
           }
        
           public void on() {
               System.out.println("projector on");
           }
        
           public void off() {
               System.out.println("projector off");
           }
        
           public void focus() {
               System.out.println("projector focus");
           }
        
        }
        
      • public class TheaterLight {
        
           // 影院灯光 使用饿汉
           public static final TheaterLight THEATER_LIGHT = new TheaterLight();
        
           private TheaterLight() {
           }
        
           public static TheaterLight getInstance() {
               return THEATER_LIGHT;
           }
        
           public void on() {
               System.out.println("theater_light on");
           }
        
           public void off() {
               System.out.println("theater_light off");
           }
        
           public void dim() {
               System.out.println("theater_light dim");
           }
        
           public void bright() {
               System.out.println("theater_light bright");
           }
        
        }
        
      • public class Stereo {
        
           // 立体声 使用饿汉
           public static final Stereo STEREO = new Stereo();
        
           private Stereo() {
           }
        
           public static Stereo getInstance() {
               return STEREO;
           }
        
           public void on() {
               System.out.println("stereo on");
           }
        
           public void off() {
               System.out.println("stereo off");
           }
        
           public void up() {
               System.out.println("stereo up");
           }
        
        }
        
        
      • public class HomeTheaterFacade {
        
           // 影院外观类,聚合其他子系统 ,提供统一的方法供Client调用
           private DVDPlayer dvdPlayer = DVDPlayer.getInstance();
           private Screen screen = Screen.getInstance();
           private Popcorn popcorn = Popcorn.getInstance();
           private Projector projector = Projector.getInstance();
           private TheaterLight theaterLight = TheaterLight.getInstance();
           private Stereo stereo = Stereo.getInstance();
        
           public HomeTheaterFacade() {
           }
        
           // 给Client提供的方法相当于子系统方法的集合
           public void ready() {
               popcorn.on();
               popcorn.pop();
               screen.dowm();
               projector.on();
               projector.focus();
               theaterLight.on();
               stereo.on();
               dvdPlayer.on();
           }
        
           public void play() {
               theaterLight.dim();
               stereo.up();
               dvdPlayer.play();
           }
        
           public void pause() {
               dvdPlayer.pause();
           }
        
           public void end() {
               popcorn.off();
               screen.up();
               projector.off();
               theaterLight.off();
               stereo.off();
               dvdPlayer.off();
           }
        
        }
        
        
      • public class Client {
           public static void main(String[] args) {
               HomeTheaterFacade homeTheaterFacade = new HomeTheaterFacade();
               System.out.println("-----------ready-----------");
               homeTheaterFacade.ready();
               System.out.println("-----------play-----------");
               homeTheaterFacade.play();
               System.out.println("-----------pause-----------");
               homeTheaterFacade.pause();
               System.out.println("-----------end-----------");
               homeTheaterFacade.end();
           }
        }
        

    mybatis源码

    • 在mybatis的configuration类中的newMetaObject方法中创建MetaObject时使用的构造方法中就用到的外观模式
    • UML类图
      • configuration类就相当于facade类

    注意事项

    • 外观模式对外屏蔽了子系统的细节,因此外观模式降低了客户端对子系统使用的复杂性
    • 外观模式对客户端与子系统的耦合关系 - 解耦,让子系统内部的模块更易维护和扩展
    • 通过合理的使用外观模式,可以帮我们更好的划分访问的
    • 当系统需要进行分层设计时,可以考虑使用Facade模式(三层架构)
    • 在维护一个遗留的大型系统时,可能这个系统已经变得非常难以维护和扩展,此时可以考虑为新系统开发一个Facade类,来提供遗留系统的比较清晰简单的接口,让新系统与Facade类交互,提高复用性
    • 不能过多的或者不合理的使用外观模式,使用外观模式好,还是直接调用模块好。要以让系统有层次,利于维护为目的
  • 相关阅读:
    2019年上半年收集到的人工智能深度学习方向干货文章
    2019年上半年收集到的人工智能自然语言处理方向干货文章
    2019年上半年收集到的人工智能图神经网络干货文章
    2019年上半年收集到的人工智能自动驾驶方向干货文章
    SAP 不支持交货单中同一个物料多个行项目HU与序列号组合发货场景
    SAP S4HANA 使用BP创建供应商报错
    yum/dnf/rpm 等 查看rpm 包安装路径 (fedora 中 pygtk 包内容安装到哪里了)
    apache 允许 访问软链接 ( Apache won't follow symlinks (403 Forbidden) )
    fedora 开启 apache 并 开启目录浏览模式
    如何在 windows server 2008 上面 挂载NFS
  • 原文地址:https://www.cnblogs.com/xiaokantianse/p/14007432.html
Copyright © 2011-2022 走看看