中介者模式(Mediator Pattern):用一个中介对象来封装一系列的对象交互,中介者使得各对象不需要显示地相互引用,从而使得耦合松散,而且可以独立地改变它们之间的交互。
面向对象设计鼓励将行为分布到各个对象中。但是,这种分布可能会导致对象间有许多连接。每一个对象都知道其他所有对象,就造成了复杂的关系。对象与对象之间存在大量的关联关系,这样势必会导致系统的结构变得很复杂,同时若一个对象发生改变,我们也需要跟踪与之相关联的对象,同时做出相应的处理。
中介者模式是用来降低多个对象和类之间的通信复杂性。这种模式提供了一个中介类,该类通常处理不同类之间的通信,并支持松耦合,使代码易于维护。中介者模式属于行为型模式。
(1)抽象中介者(Mediator)
抽象中介者用于定义一个接口,接口用于各同事之间的通信。
(2)具体中介者(ConcreteMediator)
具体中介者是抽象中介者的子类,通过协调各个同事对象来实现协作行为,了解并维护它对各个同事对象的引用。
(3)抽象同事类(Colleague)
抽象同事类定义各同事的公有方法。
(4)具体同事类(ConcreteColleague)
具体同事类是抽象同事类的子类,每一个同事对象都引用一个中介者对象;
每一个同事对象在需要和其他同事对象通信时,先与中介者通信,通过中介者来间接完成与其他同事类的通信;
(1)简化了对象之间的交互。用中介者和同事的一对多的关系代替了原来同事之间的多对交互。
(2)将各同事解耦。中介者有利于各同事之间的松耦合。
(3)减少子类生成。
在具体中介者类中包含了同事之间的交互细节,可能会导致具体中介者类非常复杂,使能系统难以维护。
(1)系统中对象之间存在复杂的引用关系,产生的相互依赖关系结构混乱难以理解。
(2)一个对象由于引用了其他很多对象并且直接和这些对象通信,导致难以复用该对象。
应用实例: 1、中国加入 WTO 之前是各个国家相互贸易,结构复杂,现在是各个国家通过 WTO 来互相贸易。 2、机场调度系统。 3、MVC 框架,其中C(控制器)就是 M(模型)和 V(视图)的中介者。
利用中介者模式实现聊天是功能。
- #include
- using namespace std;
-
- #define SAFE_DELETE(p) if (p) { delete p; p = NULL; }
- //抽象中介者
- class Mediator;
- //抽象同事类
- class Colleague
- {
- public:
- Colleague(Mediator *pMediator) : m_pMediator(pMediator){}
-
- virtual void Send(char *message) = 0;
-
- protected:
- Mediator *m_pMediator;
- };
-
- //具体同事类1
- class ConcreteColleague1 : public Colleague
- {
- public:
- ConcreteColleague1(Mediator *pMediator) : Colleague(pMediator){}
-
- void Send(char *message);
-
- void Notify(char *message)
- {
- wcout<
- }
- };
- //具体同事类2
- class ConcreteColleague2 : public Colleague
- {
- public:
- ConcreteColleague2(Mediator *pMediator) : Colleague(pMediator){}
-
- void Send(char *message);
-
- void Notify(char *message)
- {
- cout<<"ConcreteColleague2 is handling the message."<
- wcout<
- }
- };
-
- //抽象中介者类
- class Mediator
- {
- public:
- virtual void Sent(char *message, Colleague *pColleague) = 0;
- };
-
- //具体中介者类
- class ConcreteMediator : public Mediator
- {
- public:
- // The mediator forward the message
- void Sent(char *message, Colleague *pColleague)
- {
- ConcreteColleague1 *pConcreteColleague1 = dynamic_cast
(pColleague); - if (pConcreteColleague1)
- {
- cout<<"The message is from ConcreteColleague1. Now mediator forward it to ConcreteColleague2"<
- if (m_pColleague2)
- {
- m_pColleague2->Notify(message);
- }
- }
- else
- {
- if (m_pColleague1)
- {
- m_pColleague1->Notify(message);
- }
- }
- }
-
- void SetColleague1(Colleague *pColleague)
- {
- m_pColleague1 = dynamic_cast
(pColleague); - }
-
- void SetColleague2(Colleague *pColleague)
- {
- m_pColleague2 = dynamic_cast
(pColleague); - }
-
- private:
- // The Mediator knows all the Colleague
- ConcreteColleague1 *m_pColleague1;
- ConcreteColleague2 *m_pColleague2;
- };
-
- void ConcreteColleague1::Send(char *message)
- {
- // The second parameter mark where the message comes from
- m_pMediator->Sent(message, this);
- }
-
- void ConcreteColleague2::Send(char *message)
- {
- m_pMediator->Sent(message, this);
- }
-
- int main()
- {
- // Create the mediator
- Mediator *pMediator = new ConcreteMediator();
-
- Colleague *pColleague1 = new ConcreteColleague1(pMediator);
- Colleague *pColleague2 = new ConcreteColleague2(pMediator);
-
- ConcreteMediator *pConcreteMediator = dynamic_cast
(pMediator); - pConcreteMediator->SetColleague1(pColleague1);
- pConcreteMediator->SetColleague2(pColleague2);
-
- char message[260] = "Where are you from?";
- pColleague1->Send(message);
-
- return 0;
- }
输出信息:
The message is from ConcreteColleague1. Now mediator forward it to ConcreteColleague2
ConcreteColleague2 is handling the message.
Where are you from?
6 中介者与外观者模式的区别
外观模式与中介者模式的不同之处在于,外观模式是对一个对象子系统进行抽象,从而提供了一个更为方便的接口;外观模式的协议是单向的,即外观模式向子系统提出请求,但反过来则不行;而对于中介者模式,是进行多个对象之间的协作,通信是多向的。
参考文献:
【1】C++设计模式——中介者模式 - Ring_1992 - 博客园
【2】中介者模式 | 菜鸟教程
-
相关阅读:
AcWing-C/C++语法基础【合集2】
数字IC笔试题和回答整理
虚拟网络编辑器三种模式工作原理详细介绍(桥接-网络地址转换-主机模式)
x64 简介
Keepalived+LVS高可用集群
[附源码]JAVA毕业设计个人饮食营养管理信息系统(系统+LW)
【面试:并发篇38:多线程:线程池】ThreadPoolExecutor类的基本概念
数据分析-Pandas数据探查初步:离散点图
C# excel操作
永久关闭win10系统自动更新以及如何部署虚拟机以win xp为例
-
原文地址:https://blog.csdn.net/kenjianqi1647/article/details/122951386