三分钟理解“中介者模式”——设计模式轻松掌握

中介者模式的官方定义:

中介者模式使用一个中介对象来封装一系列对象的交互,从而使各对象不需要显式的相互引用,从而使得对象我们耦合松散,而且可以独立地改变对象之间的交互。

普通情况下ColleagueA向ColleagueB、ColleagueC、ColleagueD对象发送消息:

1.首先,在ColleagueA类中需要有一个sendMessage函数,用于向指定的对象发送消息;

2.其次,所有需要接收消息的对象都必须实现Colleague接口,并实现其中的getMessage函数,用于接收消息。

3.sendMessage()函数的实现如下:

private ColleagueB b = new ColleagueB();

private ColleagueC c = new ColleagueC();

private ColleagueD d = new ColleagueD();

public boolean sendMessage(String mess,Colleague colleague){

if(colleague instanceof(ColleagueB))

b.getMessage(message);

else if(colleague instanceof(ColleagueB))

c.getMessage(message);

else if(colleague instanceof(ColleagueB))

d.getMessage(message);

}

在ColleagueA中必须要先创建ColleagueB、ColleagueC、ColleagueD三个对象,然后调用他们各自的getMessage函数给他们发送消息。

在这种方式中,ColleagueA直接向三个对象发送消息,也就是ColleagueA必须要拥有其他三个对象的引用,这样导致ColleagueA与其他三个对象的藕合度高;若要增加消息接收者的时候,就必须要修改ColleagueA中的代码,这违背了“开放扩展,封闭修改”的原则。

使用“中介者模式”向ColleagueA向ColleagueB、ColleagueC、ColleagueD对象发送消息:

引入中介者之后,ColleagueA中只需要包含Mediator对象,无需发送函数;ColleagueA若要向ColleagueB、ColleagueC、ColleagueD发送消息,只需调用Mediator对象的sendMessage(message,colleague)即可。

由于A只与Mediator打交道,与B、C、D并没有直接的关系,因此实现了A与BCD之间的松藕合。

若要增加接收消息的类,只需在Mediator中增加代码,而无需修改ColleagueA中的代码,从而体现了“开放扩展,封闭修改”。

PS:“开放-封闭”原则是针对客户端而言的,是指当调用者/用户使用了一个类库之后,如果类库的功能要增强的时候,客户端代码应该是不需要做任何修改的,这就体现了“封闭修改”的原则,也就是“封闭修改”是针对客户端而言的,被调用的类库中仍然可能有部分代码需要修改,这是允许的。

中介者模式的优点:

Mediator的出现减少了各个Colleague之间的藕合,使得可以独立地改变和复用各个Colleague和Mediator;

其次,由于把对象如何协作进行了抽象,将中介作为一个独立的概念并将其封装在一个对象中,这样关注的对象就从对象各自本身的行为转移到它们之间的交互上来,也就是站在一个更宏观的角度去看待系统。

中介者模式的缺点:

由于Mediator中包含了所有的Colleague对象,所有的控制都在Mediator的sendMessage函数中实现,从而使得中介者过于复杂。

何时运用?

中介者模式一般应用于一组对象之间的通信较为复杂,采用中介者连接所有对象,从而降低各个对象之间的藕合度。

本文参与腾讯云自媒体分享计划,欢迎正在阅读的你也加入,一起分享。

发表于

我来说两句

0 条评论
登录 后参与评论

相关文章

来自专栏码代码的陈同学

Java中的类加载器

Class loaders属于JRE的一部分,负责在运行时将Java类动态加载到JVM。得益于class loaders,JVM在无需知晓底层文件或文件系统时就...

1172
来自专栏向治洪

Koa源码分析

Koa 是一个类似于 Express 的Web开发框架,创始人也都是TJ。Koa 的主要特点是,使用了 ES6 的 Generator 函数,进行了架构的重新设...

2976
来自专栏Android中高级开发

Android并发编程 多线程与锁

该文章是一个系列文章,是本人在Android开发的漫漫长途上的一点感想和记录,如果能给各位看官带来一丝启发或者帮助,那真是极好的。

2662
来自专栏JavaEdge

类加载器与双亲委派模型1 类加载器 2 双亲委派模型

类加载器(ClassLoader)是Java语言的一项创新,也是Java流行的一个重要原因。 在类加载的第一阶段“加载”过程中,需要通过一个类的全限定名来获取...

1672
来自专栏FreeBuf

FlaskJinja2 开发中遇到的的服务端注入问题研究 II

0x00. 前言 本篇文章是 《Flask Jinja2 开发中遇到的的服务端注入问题研究》<点击阅读原文查看链接>续篇,我们继续研究 Flask Jinja...

2856
来自专栏java一日一条

Java 多线程同步的五种方法

因为当我们有多个线程要同时访问一个变量或对象时,如果这些线程中既有读又有写操作时,就会导致变量值或对象的状态出现混乱,从而导致程序异常。举个例子,如果一个银行账...

1722
来自专栏高爽的专栏

Java线程(四):线程中断、线程让步、线程睡眠、线程合并

最近在Review线程专栏,修改了诸多之前描述不够严谨的地方,凡是带有Review标记的文章都是修改过了。本篇文章是插进来的,因为原来没有写,现在...

2680
来自专栏程序员宝库

【译】深入研究 Laravel 的依赖注入容器

原文地址:Laravel's Dependency Injection Container in Depth 下面是中文翻译。 Laravel拥有强大的控制反转...

6177
来自专栏李家的小酒馆

Java面试基本知识

Java基本知识 基本知识 服务器:Tomcat 支持Servlet jsp JBoss 开源应用服务器 Apache:最广泛的http服务器,只支持静态网页 ...

2940
来自专栏开源优测

BeautifulSoup的使用

参考资料地址:https://www.crummy.com/software/BeautifulSoup/bs4/doc.zh/#id28

1241

扫码关注云+社区

领取腾讯云代金券