【设计模式】21.行为型模式-中介者(Mediator)
一、描述
定义一个中介对象来简化原有对象之间的交互关系,降低系统中对象间的耦合度,使原有对象之间不必相互了解。
角色:
1.抽象中介类:它是中介者的接口,提供了同事对象注册与转发同事对象信息的抽象方法
2.具体中介类:实现中介者接口,定义一个 List 来管理同事对象,协调各个同事角色之间的交互关系,因此它依赖于同事角色。
3.抽象同事类:定义同事类的接口,保存中介者对象,提供同事对象交互的抽象方法,实现所有相互影响的同事类的公共功能。
4.具体同事类:是抽象同事类的实现者,当需要与其他同事对象交互时,由中介者对象负责后续的交互。
类图:
二、优点
1.类之间各司其职,符合迪米特法则。
2.降低了对象之间的耦合性,使得对象易于独立地被复用。
3.将对象间的一对多关联转变为一对一的关联,提高系统的灵活性,使得系统易于维护和扩展。
三、缺点
1.中介者模式将原本多个对象之间的相互依赖变成了中介者和多个同事类的依赖关系。当同事类越多时,中介者就会越臃肿,变得复杂且难以维护。
四、适用场景
1.当对象之间存在复杂的网状结构关系而导致依赖关系混乱且难以复用时。
2.当想创建一个运行于多个类之间的对象,又不想生成新的子类时。
五、示例
以“QQ聊天”为例
1.抽象同事类
public abstract class AbstractColleague { protected AbstractMediator mediator; public void setMediator(AbstractMediator mediator) { this.mediator = mediator; } public abstract void send(String msg); public abstract void receive(); }
2.抽象中介类
public abstract class AbstractMediator { protected List<AbstractColleague> colleagues = new ArrayList<>(); public void addColleague(AbstractColleague colleague) { this.colleagues.add(colleague); } public abstract void transMsg(AbstractColleague excludeColleague); }
3.具体同事类
public class FriendAColleague extends AbstractColleague { @Override public void send(String msg) { System.out.println("A消息发出:" + msg); mediator.transMsg(this); } @Override public void receive() { System.out.println("A消息接收:好的呀"); } }
public class FriendBColleague extends AbstractColleague { @Override public void send(String msg) { System.out.println("B消息发出:" + msg); mediator.transMsg(this); } @Override public void receive() { System.out.println("B消息接收:好的呀"); } }
public class FriendCColleague extends AbstractColleague { @Override public void send(String msg) { System.out.println("C消息发出:" + msg); mediator.transMsg(this); } @Override public void receive() { System.out.println("C消息接收:好的呀"); } }
4.具体中介者类
public class QQMediator extends AbstractMediator { @Override public void transMsg(AbstractColleague excludeColleague) { for (AbstractColleague colleague : colleagues) { if (!Objects.equal(colleague, excludeColleague)) { colleague.receive(); } } } }
5.测试类
public class Client { public static void main(String[] args) { QQMediator qqMediator = new QQMediator(); FriendAColleague friendAColleague = new FriendAColleague(); friendAColleague.setMediator(qqMediator); FriendBColleague friendBColleague = new FriendBColleague(); friendBColleague.setMediator(qqMediator); FriendCColleague friendCColleague = new FriendCColleague(); friendCColleague.setMediator(qqMediator); qqMediator.addColleague(friendAColleague); qqMediator.addColleague(friendBColleague); qqMediator.addColleague(friendCColleague); friendAColleague.send("咱们中午去吃铁板烧吧。"); } }
测试结果:
六、与观察者区别
一个不错的区分二者关系的文章,推荐给大家:https://www.cnblogs.com/yaopengfei/p/13502916.html
【推荐】国内首个AI IDE,深度理解中文开发场景,立即下载体验Trae
【推荐】编程新体验,更懂你的AI,立即体验豆包MarsCode编程助手
【推荐】抖音旗下AI助手豆包,你的智能百科全书,全免费不限次数
【推荐】轻量又高性能的 SSH 工具 IShell:AI 加持,快人一步
· 分享一个免费、快速、无限量使用的满血 DeepSeek R1 模型,支持深度思考和联网搜索!
· 基于 Docker 搭建 FRP 内网穿透开源项目(很简单哒)
· ollama系列01:轻松3步本地部署deepseek,普通电脑可用
· 25岁的心里话
· 按钮权限的设计及实现