中介者模式目的是将对象间的交互封装在一个对象中,从而使用各对象间的相互依赖解耦,并可以独立更改对像间的交互。在实际项目开发过程中,因某些原因(如:业务逻辑处理不当或设计不当等)使得多个不同对象间需要相互(引用)访问,无形当中使得原本几个不相干的或相对较为独立的几个模块产生了相互依赖。随着依赖程度的恶化,后期项目维护将是十分被动的。举个大家可能平时都有遇到过的例子,A界面点击了某个按钮,导致B界面需要关掉。许多人(尤其是新手程序员)总是在A界面的按钮事件响应时调用了B界面的close()行为。接着可能又由于某些需求,B界面的某些行为执行时,会影响到A、C界面等等,明显的,原本这些不相干的界面现在都产生了相互依赖,如此必定会影响后期的维护。此时,一种解决手段就可以使用该中介者模式。先看下没有使用中介者模式与使用中介者模式两种情况的对象交互情况。
由上所述可明显看出该模式的目的意图,下面是中介者模式的类关系图参考结构:
模式的编码结构参考如下:
1 namespace mediator 2 { 3 // 4 // 此处只设计简单的中介者对象,如果有必要,Mediator的设计,完全可以考虑使用Observer 5 // 模式来设计。使用Observer模式来设计Mediator,则相对会更通用些,当然设计也相对更为 6 // 复杂些。如果实际情况较为简单时,则只需要使用简单方式实现Mediator即可(参考如下)。 7 // 8 9 // 各模块对象类型 10 class ModuleA {}; 11 class ModuelB {}; 12 class ModuelC 13 { 14 public: 15 void doSomething() {} 16 }; 17 class ModuelD 18 { 19 public: 20 void doSomething() {} 21 }; 22 class ModuelE {}; 23 24 // 中介者对象类型,此处不再弄个基类. 25 class Mediator 26 { 27 public: 28 void actionA() { 29 // some code here.such as below. 30 m_pModuleC->doSomething(); 31 m_pModuleD->doSomething(); 32 } 33 // some other code here........ 34 35 private: 36 ModuleA* m_pModuleA; 37 ModuelB* m_pModuleB; 38 ModuelC* m_pModuleC; 39 ModuelD* m_pModuleD; 40 ModuelE* m_pModuleE; 41 }; 42 43 }//namespace mediator
Mediator模式编码结构参考
Mediator模式重在将几个处于“同级别”(或称为同层次结构上)的模块对象的依赖解耦。即:如上的各个模块间,它们并不存在明显的上下层次关系,它们是处于同一层次层面的对象。比如两个维护着不同模块的数据的数据维护对象class ClanDataMgr;和class ChatDataMgr;一般情况下,这两个对象间是没有交集的,但由于某些原因,开发者让他们间产生了交集(注意:这只是个举例而已)。之前在介绍结构型模式时,也有一个模式也是解决类似这种依赖性错综复杂的依赖关系问题,该模式是:Facade模式。但Facade模式意图是将应用对子系统的依赖解耦,即:应用与子系统间是存在明显的上下层依赖关系,这也是Facade模式与Mediator模式的不同之处。
在设计Mediator时,如果实际情况较为复杂,还需要考虑日后交互的变动。比如可参考上述类关系参考图中的抽象IMediaotr设计方案,又或者考虑使用Strategy模式方案等等。如果实际情况较为简单,模块对象间的交互又相对较为固定,则使用简单设计Mediator即可。实际如果设计,最终还是视具体项目情况分析而定。