十、结构型(外观模式)

外观模式(Facade Pattern)

概念
外观模式(Facade Pattern)是一种结构型设计模式,旨在为复杂子系统提供一个简化的统一接口。通过外观模式,客户端可以与子系统交互,而无需了解子系统的内部复杂性。这种模式为客户端屏蔽了复杂系统的细节,使得客户端使用系统时变得更简单。


应用场景

  1. 简化客户端与复杂系统的交互:在一个复杂的系统中,如果客户端需要与多个子系统进行交互,外观模式通过提供一个简化的接口,隐藏了系统的复杂性。例如,图形系统、数据库操作、第三方接口等往往有多个复杂的接口,外观模式可以为这些接口提供统一入口。

  2. 减少类之间的耦合:客户端只需与外观类交互,而不需要直接调用多个子系统接口,从而降低了客户端与子系统之间的耦合度,增强了系统的可维护性。

  3. 层次化结构:外观模式可以用于设计层次化系统,每一层提供一个外观类,减少上下层的相互依赖。例如,Web应用程序中,业务层可能会通过外观类来调用底层的持久化层和其他服务。


注意点

  • 外观类不应包含太多业务逻辑:外观类的职责应是简化接口,而不是实现复杂的业务逻辑。实际业务逻辑应由子系统负责处理。
  • 外观模式并不强制子系统内部结构的简化:它只是对客户端提供了一个简化的接口,子系统内部仍然可能非常复杂。
  • 可扩展性问题:如果子系统发生变化,外观类可能需要随着调整。

核心要素

  1. Facade(外观类):为客户端提供简化的接口,封装复杂的子系统接口调用。
  2. Subsystem(子系统类):复杂子系统的一部分,通常是多个类组成的系统,外观类通过这些子系统类完成各种功能。
  3. 客户端(Client):使用外观类来与子系统交互,客户端无需知道子系统的细节。

Java代码完整示例

// 子系统A
class SubsystemA {public void operationA() {System.out.println("子系统A的操作");}
}// 子系统B
class SubsystemB {public void operationB() {System.out.println("子系统B的操作");}
}// 子系统C
class SubsystemC {public void operationC() {System.out.println("子系统C的操作");}
}// 外观类
class Facade {private SubsystemA subsystemA;private SubsystemB subsystemB;private SubsystemC subsystemC;public Facade() {subsystemA = new SubsystemA();subsystemB = new SubsystemB();subsystemC = new SubsystemC();}// 提供简化的接口public void performOperation() {subsystemA.operationA();subsystemB.operationB();subsystemC.operationC();}
}// 客户端
public class Client {public static void main(String[] args) {Facade facade = new Facade();facade.performOperation();}
}

输出结果

子系统A的操作
子系统B的操作
子系统C的操作

各种变形用法完整示例

  1. 分层外观模式
    在复杂系统中,多个子系统可能会存在多层次的依赖关系,可以为每一层提供一个外观类。例如,在一个大型企业级系统中,可以有数据层、业务逻辑层和表示层的外观类。

    代码示例

    // 数据层外观类
    class DataLayerFacade {private SubsystemA subsystemA;private SubsystemB subsystemB;public DataLayerFacade() {subsystemA = new SubsystemA();subsystemB = new SubsystemB();}public void dataLayerOperation() {subsystemA.operationA();subsystemB.operationB();}
    }// 业务层外观类
    class BusinessLayerFacade {private DataLayerFacade dataLayerFacade;private SubsystemC subsystemC;public BusinessLayerFacade() {dataLayerFacade = new DataLayerFacade();subsystemC = new SubsystemC();}public void businessLayerOperation() {dataLayerFacade.dataLayerOperation();subsystemC.operationC();}
    }// 客户端
    public class ClientLayered {public static void main(String[] args) {BusinessLayerFacade businessLayerFacade = new BusinessLayerFacade();businessLayerFacade.businessLayerOperation();}
    }
    
  2. 双重外观模式
    双重外观模式是将多个外观模式结合使用,客户端可以选择使用不同的外观类来访问不同的子系统。例如,一个系统可能包含多个独立模块,每个模块有自己的外观类,客户端可以选择使用特定模块的外观类。

    代码示例

    // 外观A
    class FacadeA {private SubsystemA subsystemA;private SubsystemB subsystemB;public FacadeA() {subsystemA = new SubsystemA();subsystemB = new SubsystemB();}public void operationA() {subsystemA.operationA();subsystemB.operationB();}
    }// 外观B
    class FacadeB {private SubsystemC subsystemC;public FacadeB() {subsystemC = new SubsystemC();}public void operationB() {subsystemC.operationC();}
    }// 客户端
    public class ClientMultipleFacades {public static void main(String[] args) {FacadeA facadeA = new FacadeA();facadeA.operationA();FacadeB facadeB = new FacadeB();facadeB.operationB();}
    }
    
  3. 与单例模式结合的外观模式
    外观模式常与单例模式结合使用,以确保系统中的外观类只有一个实例,减少系统开销,确保统一的接口访问。

    代码示例

    // 外观类使用单例模式
    class SingletonFacade {private static SingletonFacade instance;private SubsystemA subsystemA;private SubsystemB subsystemB;private SingletonFacade() {subsystemA = new SubsystemA();subsystemB = new SubsystemB();}public static SingletonFacade getInstance() {if (instance == null) {instance = new SingletonFacade();}return instance;}public void performOperations() {subsystemA.operationA();subsystemB.operationB();}
    }// 客户端
    public class ClientSingletonFacade {public static void main(String[] args) {SingletonFacade facade = SingletonFacade.getInstance();facade.performOperations();}
    }
    

总结
外观模式的主要作用是简化客户端对复杂系统的访问。通过引入外观类,系统的可维护性、可扩展性和模块化得到了提升。装饰者模式和外观模式的不同之处在于,装饰者模式注重在运行时增加功能,而外观模式侧重于为子系统提供一个简化的接口。

本文来自互联网用户投稿,该文观点仅代表作者本人,不代表本站立场。本站仅提供信息存储空间服务,不拥有所有权,不承担相关法律责任。如若转载,请注明出处:http://www.rhkb.cn/news/453128.html

如若内容造成侵权/违法违规/事实不符,请联系长河编程网进行投诉反馈email:809451989@qq.com,一经查实,立即删除!

相关文章

【Pycharm】显示内存不足the IDE is running low on memory解决方法

Pycharm提示显示内存不足the IDE is running low on memory解决方法 在右上角找到Help,点击,找到change memory settings 修改数值如1024,2048 等,增大容量即可。最后点击save and Restart

【Android】Jetpack入门知识总结(LifeCycle,ViewModel,LiveData,DataBinding等)

文章目录 LifeCycle使用Lifecycle解耦页面与组件自定义控件实现LifecycleObserver接口注册生命周期监听器 使用LifecycleService解耦Service与组件使用ProcessLifecycleOwner监听应用程序生命周期 ViewModel用法在 Fragment 中使用 ViewModel LiveDataDataBinding导入依赖基本用…

2024_E_100_连续字母长度

连续字母长度 题目描述 给定一个字符串&#xff0c;只包含大写字母&#xff0c;求在包含同一字母的子串中&#xff0c;长度第 k 长的子串的长度&#xff0c;相同字母只取最长的那个子串。 输入描述 第一行有一个子串(1<长度<100)&#xff0c;只包含大写字母。 第二行为…

傅里叶分析之掐死教程(完整版)更新于2014.06.06

作 者&#xff1a;韩 昊 知 乎&#xff1a;Heinrich 微 博&#xff1a;花生油工人 知乎专栏&#xff1a;与时间无关的故事 谨以此文献给大连海事大学的吴楠老师&#xff0c;柳晓鸣老师&#xff0c;王新年老师以及张晶泊老师。 转载的同学请保留上面这句话&#xff0c;谢谢。如果…

stable diffusion WEBUI Brief summary

1&#xff0c;rembg(去除背景-》蒙版) import rembg from PIL import Image, ImageOps import numpy as np# 打开图像 input_path "./p_6258838.jpg" input_image Image.open(input_path)# 移除背景&#xff0c;得到带有透明背景的图像 output_image rembg.remove…

IO编程--两进程间的实时通信

一、使用有名管道实现两个进程之间的相互通信 代码如下&#xff1a; 创建有名管道文件 #include <myhead.h> int main(int argc, const char *argv[]) {if(mkfifo("myfifo",0664)-1){perror("create error");return -1;}if(mkfifo("myfifo_1&qu…

UDP/TCP协议详解

目录 一,自定义应用层协议: 1)xml 2),JSON 3),yml 4),google protobuffer 二,传输层UDP/TCP: UDP协议: TCP协议: TCP的核心机制一:确认应答 TCP核心机制二:超时重传 TCP核心机制三:连接管理 TCP核心机制四:滑动窗口 TCP核心机制五:流量控制 TCP核心机制六:拥塞控制…

基于springboot的网上服装购物商城系统

基于springboot的网上服装购物商城系统 开发语言&#xff1a;Java 框架&#xff1a;springboot JDK版本&#xff1a;JDK1.8 服务器&#xff1a;tomcat7 数据库&#xff1a;mysql 5.7 数据库工具&#xff1a;Navicat11 开发软件&#xff1a;idea 源码获取&#xff1a; &#x…

Video-LLaMA论文解读和项目部署教程

Video-LLaMA: An Instruction-tuned Audio-Visual Language Model for Video Understanding 相关工作 大型语言模型: 本文的工作基于这些LLM,并提供即插即用插件,使其能够理解视频中的视觉和听觉内容。 多模态大型语言模型: 现有的方法可以分为两大类。 第一类包括使用LL…

【Word原件测试资料合集】软件系统功能测试方案,软件测试方案(整体方案),软件测试文档-测试计划模版(功能与性能),软件测试流程

一、 前言 &#xff08;一&#xff09; 背景 &#xff08;二&#xff09; 目的 &#xff08;三&#xff09; 测试目标 &#xff08;四&#xff09; 适用范围与读者对象 &#xff08;五&#xff09; 术语与缩写 二、 软件测试实施流程 &#xff08;一&#xff09; 测试工作总体流…

stm32驱动W2812

W2812简介 W2812 内置有控制电路和 RGB LED 灯珠&#xff0c;用户只需通过一条数据线进行控制 每一个LED的R、G、B分别由八位数据控制颜色浓度&#xff0c;&#xff08;每种颜色浓度有0~255档&#xff0c;理论上RGB就可以组成256的3次方中颜色组合&#xff09;即每个LED需要…

基于MATLAB的混沌序列图像加密程序

设计目的 图像信息生动形象&#xff0c;它已成为人类表达信息的重要手段之一&#xff0c;网络上的图像数据很多是要求发送方和接受都要进行加密通信&#xff0c;信息的安全与保密显得尤为重要&#xff0c;因此我想运用异或运算将数据进行隐藏&#xff0c;连续使用同一数据对图…

【Eclipse系列】解决Eclipse中xxx.properties文件中文乱码问题

问题描述&#xff1a;由于eclipse对Properties资源文件的编码的默认设置是ISO-8859-1&#xff0c;所以在打开.properties文件时&#xff0c;会发现中文乱码了&#xff0c;如图&#xff1a; 解决方法&#xff1a; 1、一次生效法 右击该properties文件–>properties–>Re…

力扣2653.滑动窗口的美丽值

给你一个长度为 n 的整数数组 nums &#xff0c;请你求出每个长度为 k 的子数组的 美丽值 。 一个子数组的 美丽值 定义为&#xff1a;如果子数组中第 x 小整数 是 负数 &#xff0c;那么美丽值为第 x 小的数&#xff0c;否则美丽值为 0 。 请你返回一个包含 n - k 1 个整数…

__问题——进入启动文件_卡死在Default_Handler_死机

MCU&#xff1a;STM32F407VET6 先说结论&#xff0c;调试时跳转到启动文件里的死循环&#xff0c;只要不是硬件错误中断&#xff0c;那么多半是因为中断处理函数没有定义导致的。 【历程】 今天在测试最小单片机系统时&#xff0c;定义了一个按键处理&#xff0c;依赖的是外部中…

全网免费的文献调研方法以及获取外网最新论文、代码和翻译pdf论文的方法(适用于硕士、博士、科研)

1. 文献调研 学术搜索引擎(十分推荐前三个&#xff0c;超有用)&#xff1a;使用 Google Scholar(https://scholar.google.com/)(https://scholar.google.com.tw/)(巨人学术搜索‬‬)、&#xff08;三个都可以&#xff0c;镜像网站&#xff09; arXiv(https://arxiv.org/)、&am…

【python】OpenCV—Sort the Point Set from Top Left to Bottom Right

文章目录 1、功能描述2、代码实现3、效果展示4、更多例子5、参考 1、功能描述 给出一张图片&#xff0c;里面含有各种图形&#xff0c;取各种图形的中心点&#xff0c;从左到右从上到下排序 例如 2、代码实现 import cv2 import numpy as npdef process_img(img):img_gray c…

【计算机网络原理】GBN,SR,TCP区别以及案例介绍

概念介绍 GBN、SR和TCP协议的主要区别在于它们的重传机制、确认方式以及缓存机制的不同。‌ GBN&#xff08;Go-Back-N&#xff09;协议在数据传输中&#xff0c;如果某个报文段没有被正确接收&#xff0c;那么从这个报文段到后面的所有报文段都需要重新发送。GBN采用累计应答…

网络安全基础知识点_网络安全知识基础知识篇

文章目录 一、网络安全概述1.1 定义1.2 信息安全特性1.3 网络安全的威胁1.4 网络安全的特征 二、入侵方式2.1 黑客2.1.1 入侵方法2.1.2 系统的威胁2.2 IP欺骗与防范2.2.1 TCP等IP欺骗基础知识2.2.2 IP欺骗可行的原因2.2.3 IP欺骗过程2.2.4 IP欺骗原理2.2.5 IP欺骗防范2.3 Sniff…