Facade模式——设计模式学习(转载)
Facade模式
一 意图
为子系统中的一组接口提供一个一致的界面,Facade模式定义了一个高层接口,这个接口使得这一子系统更加容易使用。
二 动机
将一个系统划分成为若干个子系统有利于降低系统的复杂性。一个常见的设计目标是使子系统间的通信和相互依赖关系达到最小。
达到该目标的途径之一是就是引入一个外观(Facade)对象,它为子系统中较一般的设施提供了一个单一而简单的界面。
将各个子系统整合起来作为Facade,提供给客户端使用。
看下面这样一个系统:

转变成:

三 适用性及其结构
- 当你要为一个复杂子系统提供一个简单接口时。
- 客户程序与抽象类的实现部分之间存在着很大的依赖性。
- 当你需要构建一个层次结构的子系统时,使用Facade模式定义子系统中每层的入口点。仅通过facade进行通讯。
结构:

Facede:
知道哪些子系统类负责处理请求。
将客户的请求代理给适当的子系统对象。
Subsystem classes :
实现子系统的功能。
处理由Facade对象指派的任务。
没有facade的任何相关信息;即没有指向facade的指针。
客户程序通过发送请求给Facade的方式与子系统通讯, Facade将这些消息转发给适当的子系统对象。
尽管是子系统中的有关对象在做实际工作,但Facade模式本身也必须将它的接口转换成子系统的接口。
Facade模式有助于建立层次结构系统,也有助于对对象之间的依赖关系分层。
Facade模式可以消除复杂的循环依赖关系。降低客户-子系统之间的耦合度。
使用Facade的客户程序不需要直接访问子系统对象。
四 代码实现
1 subsystemClasses
以三种信息:SMS,MMS,PUSH为例:checkReady,getContent

/*----------------------------------------------------------------*/
/* class Base */
/*----------------------------------------------------------------*/
class Base
{
public:
Base(){};
};


/*----------------------------------------------------------------*/
/* class SmsUtil */
/*----------------------------------------------------------------*/
class SmsUtil: public Base
{
#define SMS_CONTENT "I am sms content"
public:
SmsUtil(){}
bool checkReady()
{
cout<<"SmsUtil checkReady"<<endl;
return true;
}
bool getSmsContent(int msg_id,char* pContent)
{
cout<<"SmsUtil getSmsContent"<<endl;
strcpy(pContent,SMS_CONTENT);
return true;
}
}; /*----------------------------------------------------------------*/
/* class MmsUtil */
/*----------------------------------------------------------------*/
class MmsUtil: public Base
{
#define MMS_CONTENT "I am mms content"
public:
MmsUtil(){}
bool checkReady()
{
cout<<"MmsUtil checkReady"<<endl;
return true;
}
bool getMmsContent(int msg_id,char* pContent)
{
cout<<"MmsUtil getMmsContent"<<endl;
strcpy(pContent,MMS_CONTENT);
return true;
}
}; /*----------------------------------------------------------------*/
/* class PushUtil */
/*----------------------------------------------------------------*/
class PushUtil: public Base
{
#define PUSH_CONTENT "I am push content"
public:
PushUtil(){}
bool checkReady()
{
cout<<"PushUtil checkReady"<<endl;
return true;
}
bool getPushContent(int msg_id,char* pContent)
{
cout<<"PushUtil getPushContent"<<endl;
strcpy(pContent,PUSH_CONTENT);
return true;
}
};

2 Facade ——单例类

/*----------------------------------------------------------------*/
/* class MsgFacade */
/*----------------------------------------------------------------*/
enum MsgType
{
SMS,
MMS,
PUSH,
MSG_ALL
}; class MsgFacade: public Base
{
protected:
MsgFacade()
{
m_sms = new SmsUtil();
m_mms = new MmsUtil();
m_push = new PushUtil();
}
public:
static MsgFacade* getInstance()
{
if (s_instance == NULL)
{
s_instance = new MsgFacade();
} return s_instance;
}
static void closeInstance()
{
delete s_instance;
}
public:
bool checkReady(int type)
{
bool resutl = false; resutl = m_sms->checkReady();
resutl &= m_mms->checkReady();
resutl &= m_push->checkReady(); return resutl;
}
bool getMsgContent(int type,int msg_id,char* pContent)
{
switch(type)
{
case SMS:
{
m_sms->getSmsContent(msg_id,pContent);
break;
}
case MMS:
{
m_mms->getMmsContent(msg_id,pContent);
break;
}
case PUSH:
{
m_push->getPushContent(msg_id,pContent);
break;
}
default:
break;
} return true;
}
private:
SmsUtil* m_sms;
MmsUtil* m_mms;
PushUtil* m_push; static MsgFacade* s_instance;
};
MsgFacade* MsgFacade::s_instance = NULL;

3 Test

#include "facade.h" int main()
{
MsgFacade* msg = MsgFacade::getInstance();
msg->checkReady(MSG_ALL); cout<<endl;
char content[100] = {0}; msg->getMsgContent(SMS,0,content);
cout<<content<<endl; msg->getMsgContent(MMS,0,content);
cout<<content<<endl; msg->getMsgContent(PUSH,0,content);
cout<<content<<endl; return 0;
}

4 Result

SmsUtil checkReady
MmsUtil checkReady
PushUtil checkReady SmsUtil getSmsContent
I am sms content
MmsUtil getMmsContent
I am mms content
PushUtil getPushContent
I am push content

仅需要一个Facade对象,因此Facade对象通常属于Singleton 模式
Facade模式——设计模式学习(转载)的更多相关文章
- C#命令模式-设计模式学习
命令模式(Command Pattern) 概述 在软件系统中,“行为请求者”与“行为实现者”通常呈现一种“紧耦合”.但在某些场合,比如要对行为进行“记录.撤销/重做.事务”等处理,这种无法抵御变 ...
- (转载)设计模式学习笔记(十一)——Facade外观模式
(转载)http://www.cnblogs.com/kid-li/archive/2006/07/10/446904.html Facade外观模式,是一种结构型模式,它主要解决的问题是:组件的客户 ...
- 设计模式学习之路——Facade 外观模式(结构型模式)
动机: 组件的客户和组件中各种复杂的子系统有了过多的耦合,随着外部客户程序和各子系统的演化,这种过多的耦合面临很多变化的挑战.如何简化外部客户程序和系统间的交互接口?如何将外部客户程序的演化和内部子系 ...
- 一天学习两个设计模式之Facade模式(外观模式,结构型模式)
程序这东西随着时间推移,程序会越来越大,程序中的类越来越多,而且他们之间相互关联,这会导致程序结构变得越来越复杂.因此我们在使用他们时候,必须要弄清楚他们之间的关系才能使用他们. 特别是在调用大型程序 ...
- 设计模式学习之外观模式(Facade,结构型模式)(8)
1.什么是外观模式为子系统中的一组接口提供一个一致的界面,Facade模式定义了一个高层接口,这个接口使得这一子系统更加容易使用 2.为什么要使用外观模式在软件开发系统中,客户程序经常会与复杂系统的内 ...
- Java设计模式学习记录-外观模式
前言 这次要介绍的是外观模式(也称为门面模式),外观模式也属于结构型模式,其实外观模式还是非常好理解的,简单的来讲就是将多个复杂的业务封装成一个方法,在调用此方法时可以不必关系具体执行了哪些业务,而只 ...
- 设计模式--外观(Facade)模式
Insus.NET在去年有写过一篇<软件研发公司,外观设计模式(Facade)>http://www.cnblogs.com/insus/archive/2013/02/27/293606 ...
- 设计模式学习系列6 原型模式(prototype)
原型模式(prototype)用原型实例指定创建对象的种类,并且通过拷贝这些原型创建新的对象.允许一个对象再创建另外一个新对象的时候根本无需知道任何创建细节,只需要请求圆形对象的copy函数皆可. 1 ...
- php设计模式之Proxy(代理模式)和Facade(外观)设计模式
Proxy(代理模式)和Facade(外观)设计模式它们均为更复杂的功能提供抽象化的概念,但这两种实现抽象化的过程大不相同 Proxy案例中,所有的方法和成员变量都来自于目标对象,必要时,该代理能够对 ...
随机推荐
- flask框架+pygal+sqlit3搭建图形化业务数据分析平台
一. 前言 先说下主要的框架和主要的图形库的特点:(个人见解) Django:python开发的一个重量级的web框架,集成了MVC和ORM等技术,设计之初是为了使开发复杂的.数据库驱动的网站变得简单 ...
- jQuery ajax 与服务器交互方法
1.HTML <table> <tr> <td>用户名:</td> <td><input type="text" ...
- Android 开发之错误整理java.lang.SecurityException: Requires READ_PHONE_STATE: Neither user 10088 nor current process has android.permission.READ_PHONE_STATE.
java.lang.SecurityException: Requires READ_PHONE_STATE: Neither user 10088 nor current process has a ...
- 机器学习-scikit learn学习笔记
scikit-learn官网:http://scikit-learn.org/stable/ 通常情况下,一个学习问题会包含一组学习样本数据,计算机通过对样本数据的学习,尝试对未知数据进行预测. 学习 ...
- Kubernetes DNS 简介
环境 $ sudo lsb_release -a No LSB modules are available. Distributor ID: Ubuntu Description: Ubuntu 16 ...
- WPF集合控件实现分隔符(ItemsControl Splitter)
在WPF的集合控件中常常需要在每一个集合项之间插入一个分隔符样式,但是WPF的ItemsControl没有相关功能的直接实现,所以只能考虑曲线救国,经过研究,大概想到了以下两种实现方式. 先写出Ite ...
- Use “error_messages” in Rails 3.2? (raises “undefined method” error)
I am getting the following error in my Rails 3.2 functional tests: ActionView::Template::Error: unde ...
- React-Native 之 项目实战(五)
前言 本文 有配套视频,可以酌情观看. 文中内容因各人理解不同,可能会有所偏差,欢迎朋友们联系我讨论. 文中所有内容仅供学习交流之用,不可用于商业用途,如因此引起的相关法律法规责任,与我无关,如文中内 ...
- Jmeter自动化测试工具的简单使用--HTTP测试
Jmeter自动化测试工具的简单应用 1.安装Jmeter 链接: https://pan.baidu.com/s/1mhSzU68 密码: 446z 到这里下载 1.1 jmeter 将下载好的 ...
- Elasticsearch搜索之cross_fields分析
cross_fields类型采用了一种以词条为中心(Term-centric)的方法,这种方法和best_fields及most_fields采用的以字段为中心(Field-centric)的方法有很 ...