外观模式(c++实现)
外观模式
模式定义
外观模式(Facade),为子系统中的一组接口提供一个一致的界面,此模式定义了一个高层接口,这个接口使得这一子系统更加容易使用。
模式动机
- 当要为一个复杂子系统提供一个简单接口时可以使用外观模式。该接口可以满足大多数用户的需求,而且用户也可以越过外观类直接访问子系统。
- 客户程序与多个子系统之间存在很大的依赖性。引入外观类将子系统与客户以及其他子系统解耦,可以提高子系统的独立性和可移植性。
- 在层次化结构中,可以使用外观模式定义系统中每一层的入口,层与层之间不直接产生联系,而通过外观类建立联系,降低层之间的耦合度。
UML类图
源码实现
- hero.h
#ifndef HERO_H
#define HERO_H
#include <QDebug>
class Hero
{
public:
Hero(QString name):m_Name(name){}
~Hero(){}
inline void ZhongDan() { qDebug() << m_Name << " 中单";}
inline void DaYe() { qDebug() << m_Name << " 打野";}
inline void FuZhu() { qDebug() << m_Name << " 辅助";}
inline void FaYu() { qDebug() << m_Name << " 发育";}
inline void KangYa() { qDebug() << m_Name << " 抗压";}
protected:
QString m_Name;
};
class ZhenJi : public Hero
{
public:
ZhenJi():Hero("甄姬"){}
~ZhenJi(){}
};
class ZhaoYun : public Hero
{
public:
ZhaoYun():Hero("赵云"){}
~ZhaoYun(){}
};
class XiangXiang : public Hero
{
public:
XiangXiang():Hero("大小姐"){}
~XiangXiang(){}
};
class LianPo : public Hero
{
public:
LianPo():Hero("廉颇"){}
~LianPo(){}
};
class LvBu : public Hero
{
public:
LvBu():Hero("吕布"){}
~LvBu(){}
};
#endif // HERO_H
- facade.h
#ifndef FACADE_H
#define FACADE_H
/************************************
* @brief : 用外观模式封装几个不同的子系统,
* 子系统的操作统一放到外观模式的方法去
* 峡谷系统安排:
* 外观类:游戏不同的阵容组合
* 英雄类:不同的英雄,可以打不同的位置
* 外观类组合不同的英雄,得到一个胜率值
* @author : wzx
* @date : 2020-04-17
* @project : Facade
*************************************/
#include "hero.h"
class Facade
{
public:
Facade();
~Facade();
double LineUpA();
double LineUpB();
double LineUpC();
private:
XiangXiang* m_XX;
ZhaoYun* m_ZY;
LvBu* m_LB;
LianPo* m_LP;
ZhenJi* m_ZJ;
};
#endif // FACADE_H
- facade.cpp
#include "facade.h"
#define DELEOBJECT(x) if(x == nullptr) { delete x; x = nullptr;}
Facade::Facade()
{
m_XX = new XiangXiang();
m_ZY = new ZhaoYun();
m_LB = new LvBu();
m_LP = new LianPo();
m_ZJ = new ZhenJi();
}
Facade::~Facade()
{
DELEOBJECT(m_XX);
DELEOBJECT(m_ZY);
DELEOBJECT(m_LB);
DELEOBJECT(m_LP);
DELEOBJECT(m_ZJ);
}
double Facade::LineUpA()
{
m_XX->FaYu();
m_ZY->DaYe();
m_LB->KangYa();
m_LP->FuZhu();
m_ZJ->ZhongDan();
return 0.88;
}
double Facade::LineUpB()
{
m_XX->FaYu();
m_ZY->KangYa();
m_LB->DaYe();
m_LP->FuZhu();
m_ZJ->ZhongDan();
return 0.40;
}
double Facade::LineUpC()
{
m_XX->FaYu();
m_ZY->DaYe();
m_LB->ZhongDan();
m_LP->KangYa();
m_ZJ->FuZhu();
return 0.60;
}
- main.cpp
#include <QCoreApplication>
#include "facade.h"
int main(int argc, char *argv[])
{
QCoreApplication a(argc, argv);
Facade facade;
qDebug() << "胜率" << facade.LineUpA()*100 << "%" << endl;
qDebug() << "胜率" << facade.LineUpB()*100 << "%" << endl;
qDebug() << "胜率" << facade.LineUpB()*100 << "%" << endl;
return a.exec();
}
- 运行结果
"大小姐" 发育
"赵云" 打野
"吕布" 抗压
"廉颇" 辅助
"甄姬" 中单
胜率 88 %
"大小姐" 发育
"赵云" 抗压
"吕布" 打野
"廉颇" 辅助
"甄姬" 中单
胜率 40 %
"大小姐" 发育
"赵云" 抗压
"吕布" 打野
"廉颇" 辅助
"甄姬" 中单
胜率 40 %
优点
外观模式的优点
- 对客户屏蔽子系统组件,减少了客户处理的对象数目并使得子系统使用起来更加容易。通过引入外观模式,客户代码将变得很简单,与之关联的对象也很少。
- 实现了子系统与客户之间的松耦合关系,这使得子系统的组件变化不会影响到调用它的客户类,只需要调整外观类即可。
- 降低了大型软件系统中的编译依赖性,并简化了系统在不同平台之间的移植过程,因为编译一个子系统一般不需要编译所有其他的子系统。一个子系统的修改对其他子系统没有任何影响,而且子系统内部变化也不会影响到外观对象。
- 只是提供了一个访问子系统的统一入口,并不影响用户直接使用子系统类。
- 完美的体现了依赖倒转原则和迪米特法则
缺点
外观模式的缺点
- 不能很好地限制客户使用子系统类,如果对客户访问子系统类做太多的限制则减少了可变性和灵活性。
- 在不引入抽象外观类的情况下,增加新的子系统可能需要修改外观类或客户端的源代码,违背了“开闭原则”。
参考《大话设计模式》和 https://design-patterns.readthedocs.io/zh_CN/latest/index.html
外观模式(c++实现)的更多相关文章
- 设计模式(八): 从“小弟”中来类比"外观模式"(Facade Pattern)
在此先容我拿“小弟”这个词来扯一下淡.什么是小弟呢,所谓小弟就是可以帮你做一些琐碎的事情,在此我们就拿“小弟”来类比“外观模式”.在上面一篇博文我们完整的介绍了“适配器模式”,接下来我们将要在这篇博客 ...
- 设计模式(十一)外观模式(Facade Pattern)
一.引言 在软件开发过程中,客户端程序经常会与复杂系统的内部子系统进行耦合,从而导致客户端程序随着子系统的变化而变化,然而为了将复杂系统的内部子系统与客户端之间的依赖解耦,从而就有了外观模式,也称作 ...
- 每天一个设计模式-2 外观模式(Facade)
每天一个设计模式-2 外观模式(Facade) 1.生活中的示例 客户想要购买一台电脑,一般有两种方法: 1.自己DIY,客户需要知道组成电脑的所有电子器件,并且需要熟悉那些配件,对客户要求较高. ...
- 设计模式--外观模式Facade(结构型)
一.外观模式 外观模式提供了一个统一的接口,用来访问子系统中的一群接口.外观模式定义了一个高层接口,让子系统更容易被使用. 二.UML图 三.例子 举个编译器的例子,假设编译一个程序需要经过四个步骤: ...
- Objective-C 外观模式--简单介绍和使用
外观模式(Facade),为子系统中的一组接口提供一个一致的界面,定义一个高层接口,这个接口使得这一子系统更加容易使用. 在以下情况下可以考虑使用外观模式: (1)设计初期阶段,应该有意识的将不同层分 ...
- C#设计模式-外观模式
在软件开发过程中,客户端程序经常会与复杂系统的内部子系统进行耦合,从而导致客户端程序随着子系统的变化而变化,然而为了将复杂系统的内部子系统与客户端之间的依赖解耦,从而就有了外观模式,也称作 ”门面“模 ...
- C#设计模式系列:外观模式(Facade)
外观模式主要解决的问题是:当我们有多个类要处理时,往往要一个类一个类地区调用,没有复用性和扩展性.外观模式通过定义一个界面,把处理子类的过程封装成操作,主要就把用户从复杂的调用过程中解放出来. 1.外 ...
- 装饰模式 - Decorator 和 外观模式 - Facade
装饰模式 Decorator,不改变接口但动态给对象加入责任,所需功能按顺序串联起来控制,比生成子类灵活. 外观模式 Facade,让接口更简单.为子系统中的一组接口提供一个一致的界面. 参考:
- java设计模式之外观模式
外观模式概念 外观模式又称为门面模式,为子系统中的一组接口提供一个一致的界面,此模式定义了一个搞层次接口,使得这一个子系统更加容易使用.这一模式完美的体现了依赖倒转原则和迪米特法则的思想,所以是非常常 ...
- [Head First设计模式]生活中学设计模式——外观模式
系列文章 [Head First设计模式]山西面馆中的设计模式——装饰者模式 [Head First设计模式]山西面馆中的设计模式——观察者模式 [Head First设计模式]山西面馆中的设计模式— ...
随机推荐
- java 锁 简介(转)
转自 https://www.cnblogs.com/hustzzl/p/9343797.html 1. Java锁的种类 在笔者面试过程时,经常会被问到各种各样的锁,如乐观锁.读写锁等等,非常繁多, ...
- IDEA启动项目报错:Cannot open URL.Please check this URL is correct
IDEA启动项目报错:Cannot open URL.Please check this URL is correct 问题:IDEA启动SSM项目,使用的Tomcat,报错 Cannot open ...
- 文件合并cat and paste
cat 纵向合并 cat file1 file 2 paset横向合并 wc用法 sort用法
- JavaScript隐式类型转换(详解 +,-,*,/,==)
JavaScript 在 运算 或 比较 之前, 会自动进行隐式类型转换. 下面我们来仔细讲一讲 + - * / == 运算符经历了哪些过程. 类型转换 ECMAScript 运行时系统会在需要时从事 ...
- Apex_2. LiveBos两个时间求相差天数、历时
(1)获取两个时间相差天数(没有上午下午区分) var d1=ABS_DATESTRING(FStartTime,'yyyy/MM/dd'); var d2=ABS_DATESTRING(FEndTi ...
- Jasper报表 自动序列号
添加表达式:$V{REPORT_COUNT}.toString()
- weblogic-CVE-2020-2551-IIOP反序列化学习记录
CORBA: 具体的对CORBA的介绍安全客这篇文章https://www.anquanke.com/post/id/199227说的很详细,但是完全记住是不可能的,我觉得读完它要弄清以下几个点: 1 ...
- 记一次Xmrig挖矿木马排查过程
问题现象 Linux 服务器收到报警信息,主机 CPU 跑满. 自动创建运行 Docker 容器 xmrig, 导致其他运行中容器被迫停止. 问题原因 通过 top 命令可以看到有一个 xmrig 进 ...
- MySQL学习(4)
一 视图 预先定义一种对应关系,如:temp_table <-----> select * from class where student_id >10,那么这种对应关系叫做视图. ...
- 微信开发+百度AI学习:微信网页开发环境搭建
参考微信官方文档:https://mp.weixin.qq.com/wiki?t=resource/res_main&id=mp1421141115 两步即可获取微信网页开发能力 STEP1: ...