中介者
使用中介者模式来集中相关对象之间复杂的沟通和控制方式。
每个对象都会在自己的状态改变时,告诉中介者。
每个对象队徽对中介者所发出的请求做出回应。
适用性
- 一组对象以定义良好但是复杂的方式进行通信。产生的相互依赖关系结构混乱且难以理解。
- 一个对象引用其他很多对象并且直接与这些对象通信,导致难以复用该对象。
- 想定制一个分布在多个类中的行为,而又不想生成太多的子类。
典型情境
智能家居,互相之间规则复杂。
结构
Mediator - 中介者定义一个接口用于与各Colleague对象通信。
ConcreteMediator - 具体中介者通过协调各同事对象实现协作行为。了解并维护它的各个同事。
Colleague Class - 每一个同事类都知道它的中介者对象。每一个同事对象在需与其他的同事通信的时候,与它的中介者通信。
协作:
同事向一个中介者发送和接收请求。中介者在各同事间是当地转发请求以实现协作行为。
示例
1 2 3 4 5 6 7 8 9 10 11 12 13 14 15 16 17 18 19 20 21 22 23 24 25 26 27 28 29 30 31 32 33 34 35 36 37 38 39 40 41 42 43 44 45 46 47 48 49 50 51 52 53 54 55 56 57 58 59 60 61 62 63 64 65 66 67 68 69 70 71 72 73 74 75 76 77 78 79 80
| #include <iostream> class Mediator;
class Colleague { public: Colleague(Mediator* m) : m_mediator(m){} protected: Mediator* m_mediator; };
class Mediator { public: virtual void process(Colleague* c) = 0; };
class ConcreteColleague1 : public Colleague { public: ConcreteColleague1(Mediator* m) :Colleague(m){} void step1() { std::cout << "Step1" << std::endl; if (!m_mediator) return; m_mediator->process(this); } void step3() { std::cout << "Step3" << std::endl; } };
class ConcreteColleague2 : public Colleague { public: ConcreteColleague2(Mediator* m) : Colleague(m){} void step2() { std::cout << "Step2" << std::endl; if (!m_mediator) return; m_mediator->process(this); } };
class ConcreteMediator : public Mediator { public: ConcreteMediator() : Mediator(), m_cc1(NULL), m_cc2(NULL) { m_cc1 = new ConcreteColleague1(this); m_cc2 = new ConcreteColleague2(this); } virtual void process(Colleague* c) { if (!c || !m_cc1 || !m_cc2) return; if (c == m_cc1) { m_cc2->step2(); }else if (c == m_cc2) { m_cc1->step3(); } } void test_start() { if (!m_cc1) return; m_cc1->step1(); } protected: ConcreteColleague1* m_cc1; ConcreteColleague2* m_cc2; };
int main() { ConcreteMediator cm; cm.test_start(); system("Pause"); }
|
优点
- 通过将对象彼此解耦,可以增加对象的可复用性。
- 通过将控制逻辑集中,可以简化系统维护。
- 可以让对象之间所传递的消息变得简单而且大幅减少。
用途和缺点
- 中介者常常被用来协调相关的GUI组件。
- 中介者模式的缺点是,如果设计不当,中介者对象本身会变得过于复杂。
相关模式
- Facade与中介者的不同之处在于它是对一个对象子系统进行抽象,从而提供了一个更为方便的接口。它的协议是单向的,即Facade对象对这个子系统类提出请求,但反之则不行。相反,Mediator提供了各Colleague对象不支持或不能支持的协作行为,而且协议是多向的。
- Colleague可使用Observer模式与Mediator通信。
[1] 设计模式:可复用面向对象软件的基础
[2] Head First设计模式