Mediator 中介者也是属于“接口隔离”模式。
文章目录
- 1. 动机 (Motivation)
- 2. 模式定义
- 3. 结构(Structure)
- 4. 要点总结
- 5. 其他参考
1. 动机 (Motivation)
- 在软件构建过程中,经常会出现多个对象互相关联交互的情况,对象之间常常会维持一种复杂的引用关系,如果遇到一些需求的更改,这种直接的引用关系将面临不断的变化。
举例说明:比如大家经常需要考虑界面,界面上的控件,通常大家希望更改界面中的控件的时候,对应背后会有数据的data model,改界面的时候希望对应的data model也会更改,反过来,data model更改的时候,界面也跟着更改,这两种情况有时候就会导致双向的依赖关系或者直接的依赖关系。这种情况当然不合适,需求的变化就会换一个界面元素,成本就很高。中介者模式提供了一种思路来管理对象间的关联关系,避免相互交互的 对象之间的紧耦合。
- 在这种情况下,我们可使用一个“中介对象”来管理对象间的关联关系,避免相互交互的对象之间的紧耦合引用关系,从而更好地抵御变化。
2. 模式定义
用一个中介对象来封装(封装变化
)一系列的对象交互。中介者使各对象不需要显式的相互引用(编译时依赖运行时依赖
),从而使其耦合松散 (管理变化
),而且可以独立地改变它们之间的交互。
—《设计模式》GoF
最经典的依赖倒置原则,A本来依赖B,转换为A依赖IB,B依赖IA,难道A从此和B没关系了吗?不是的,你会发现运行时A和B还产生依赖关系,只不过依赖关系从编译时转换到了运行时。
3. 结构(Structure)
GoF的定义相当粗糙,很容易产生误导,不便于理解。Mediator定义了一个中介者,Colleague内部有一个指针指向了Mediator,ConcreteMediator里面又有指针指向了具体的ConcreteColleague,所以这里面最核心的关系是ConcreteColleague之间没有依赖关系(本来是直接依赖),他们都去依赖Mediator,反过来Mediator内部要依赖Colleague。所以Mediator和Colleague之间是双向依赖的关系,但ConcreteColleague之间没有依赖关系。
通过这种方式达到了依赖的解耦,下图的本质只是描述了依赖解耦,并没有描述其他的东西,甚至在现实中,ConcreteColleague并不是继承自Colleague。
上图是《设计模式》GoF中定义的Mediator 中介者的设计结构。结合上面的代码看图中最重要的是看其中稳定和变化部分,也就是下图中红框和蓝框框选的部分。
我们来画一幅图,来梳理上图中的关系,更能帮助大家在现实中掌握和运用该模式。
1、2、3、4、5号对象如果在不加约束的情况下去实现它们之间的访问关系,很有可能是1需要访问3…,他们之间的依赖呈现出下图中的关系。
希望提出一个新的对象来解耦他们之间的依赖关系,1、2、3、4、5号都是刚才提到的ConcreteColleague,创建一个M来表示Mediator,用1、2、3、4、5号分别跟中介者Mediator之间产生双向的依赖关系。当需要1调用3的时候,不要直接的1去调用3,而是1去通知M,M再去通知3,这个过程中就要牵扯到这个调用通知要定义一个消息规范,你发给M,M怎么知道消息规范是去找3呢 ? 这个是GoF中所没有定义怎么实现,这就相当灵活。举例来说,很多系统里面有数据绑定的模块,界面元素和数据模型之间不希望产生直接依赖,常常提出数据绑定类型,就是这里讲到的M,数据绑定类型会同时依赖两边,有些数据绑定模块会加观察者模式的元素在里面,这样就实现了数据模型只有一变更,不需要做任何主动动作,绑定的对象就得到触发消息,触发消息就会直接去找界面元素去更改,常见的数据绑定对象里就会定义一套数据绑定的一些协议,这些协议就会转化为对象互相通知的协议,对象的ID,对象的具体的属性,属性值,控件属性,需要传递的相关参数,作为协议定义清楚,这是GoF中不会触及的细节,这些细节在实际中又是繁琐的。宗旨是上图转换为下图,直接依赖关系转换为间接依赖关系。
Mediator 中介者模式相对于Facade门面模式是异曲同工,都是提出新的东西实现隔离,Facade门面模式是系统外于系统内之间的隔离,而Mediator 中介者模式解决的是系统内各个对象之间的依赖。Mediator 中介者模式一定是出现了大量的系统内多个对象复杂的关联关系
,可以说Mediator 中介者模式是依赖倒置原则在多个对象场景中的扩展形式。
4. 要点总结
-
将多个对象间复杂的关联关系解耦,Mediator模式将多个对象间的控制逻辑进行集中管理,变“多个对象互相关联”为“多个对象和一个中介者关联”,简化了系统的维护,抵御了可能的变化。
-
随着控制逻辑的复杂化,Mediator具体对象的实现可能相当复杂。这时候可以对Mediator对象进行分解处理
-
Facade模式是解耦系统间 (单向) 的对象关联关系;Mediator模式是解耦系统内各个对象之间 (双向)的关联关系。
5. 其他参考
C++设计模式——中介者模式