中介者模式(Mediator)详解:定义、实现及框架应用
创作时间:
作者:
@小白创作中心
中介者模式(Mediator)详解:定义、实现及框架应用
引用
CSDN
1.
https://blog.csdn.net/flzjcsg3/article/details/145603551
中介者模式(Mediator Pattern)是一种行为设计模式,旨在减少对象之间的直接依赖,通过引入一个中介者对象来协调多个对象之间的交互。这种模式特别适用于对象间存在复杂交互的场景,能够简化系统结构并降低耦合。
什么是中介者模式?
中介者模式的核心是封装对象间的交互,避免对象直接相互调用,而是通过中介者进行通信。这样,对象只需与中介者交互,而不需要知道其他对象的存在。
为什么要中介者模式?
假设有一个聊天室系统,多个用户(User)之间可以直接发送消息。如果没有中介者模式,用户之间会直接相互依赖:
class User {
private String name;
public User(String name) {
this.name = name;
}
public void sendMessage(String message, User receiver) {
System.out.println(name + " sends: " + message);
receiver.receiveMessage(message, this);
}
public void receiveMessage(String message, User sender) {
System.out.println(name + " received from " + sender.name + ": " + message);
}
}
public class ChatRoomWithoutMediator {
public static void main(String[] args) {
User alice = new User("Alice");
User bob = new User("Bob");
User charlie = new User("Charlie");
alice.sendMessage("Hi Bob!", bob);
bob.sendMessage("Hello Alice!", alice);
charlie.sendMessage("Hey everyone!", alice); // 需要手动发送给每个人
}
}
在没有中介者模式的情况下,对象之间通常会直接相互调用和依赖,导致以下问题:
- 对象间耦合度高:
○ 每个对象都需要知道其他对象的存在,并直接调用它们的方法。
○ 如果对象间的关系复杂,依赖会变得混乱,难以维护。 - 交互逻辑分散:
○ 对象间的交互逻辑分散在各个对象中,导致代码重复且难以管理。
○ 修改一个对象的逻辑可能会影响其他多个对象。 - 系统难以扩展:
○ 新增或修改对象时,可能需要修改多个相关对象的代码。
○ 系统的可扩展性和灵活性较差。 - 难以理解和维护:
○ 对象间的直接依赖关系使得代码难以理解,尤其是在对象数量多、交互复杂的情况下。
怎么实现中介者模式?
在中介者模式中有如下角色:
- Mediator(中介者接口):定义对象间通信的接口。
- ConcreteMediator(具体中介者):实现中介者接口,协调各对象间的交互。
- Colleague(同事类):定义各个对象的接口,每个同事类都知道中介者,并通过中介者与其他对象通信。
- ConcreteColleague(具体同事类):实现同事类接口,与其他对象通过中介者交互。
【案例】聊天室 - 改
Mediator(中介者接口):
interface ChatMediator {
void sendMessage(String message, User sender);
void addUser(User user);
}
ConcreteMediator(具体中介者):
class ChatRoom implements ChatMediator {
private List<User> users = new ArrayList<>();
@Override
public void addUser(User user) {
users.add(user);
}
@Override
public void sendMessage(String message, User sender) {
for (User user : users) {
if (user != sender) { // 不发送给自己
user.receiveMessage(message);
}
}
}
}
Colleague(同事类):
class User {
private String name;
private ChatMediator mediator;
public User(String name, ChatMediator mediator) {
this.name = name;
this.mediator = mediator;
}
public void sendMessage(String message) {
System.out.println(name + " sends: " + message);
mediator.sendMessage(message, this);
}
public void receiveMessage(String message) {
System.out.println(name + " received: " + message);
}
}
测试类:
public class ChatRoomWithMediator {
public static void main(String[] args) {
ChatMediator chatRoom = new ChatRoom();
User alice = new User("Alice", chatRoom);
User bob = new User("Bob", chatRoom);
User charlie = new User("Charlie", chatRoom);
chatRoom.addUser(alice);
chatRoom.addUser(bob);
chatRoom.addUser(charlie);
alice.sendMessage("Hi everyone!");
bob.sendMessage("Hello Alice!");
}
}
中介者模式在框架源码中的运用
Java 中的 java.util.Timer
Timer 类可以看作是一个中介者,它负责调度和管理多个 TimerTask 对象。TimerTask 是具体的同事类,它们通过 Timer 来协调任务的执行。
- Timer 作为中介者,负责调度和执行任务。
- TimerTask 不需要知道其他任务的存在,只需通过 Timer 来安排自己的执行。
import java.util.Timer;
import java.util.TimerTask;
public class TimerExample {
public static void main(String[] args) {
Timer timer = new Timer(); // 中介者
TimerTask task1 = new TimerTask() {
@Override
public void run() {
System.out.println("Task 1 is running.");
}
};
TimerTask task2 = new TimerTask() {
@Override
public void run() {
System.out.println("Task 2 is running.");
}
};
// 通过中介者安排任务
timer.schedule(task1, 1000); // 1秒后执行
timer.schedule(task2, 2000); // 2秒后执行
}
}
Spring 框架中的 ApplicationContext
在 Spring 框架中,ApplicationContext 可以看作是一个中介者,它负责管理 Bean 的创建、依赖注入和生命周期。
- ApplicationContext 作为中介者,集中管理所有 Bean 的交互。
- Bean 之间不需要直接依赖,而是通过 ApplicationContext 获取依赖。
import org.springframework.context.ApplicationContext;
import org.springframework.context.annotation.AnnotationConfigApplicationContext;
class ServiceA {
public void doSomething() {
System.out.println("Service A is doing something.");
}
}
class ServiceB {
private final ServiceA serviceA;
public ServiceB(ServiceA serviceA) {
this.serviceA = serviceA;
}
public void doSomething() {
System.out.println("Service B is doing something.");
serviceA.doSomething();
}
}
public class SpringExample {
public static void main(String[] args) {
ApplicationContext context = new AnnotationConfigApplicationContext(AppConfig.class);
ServiceB serviceB = context.getBean(ServiceB.class);
serviceB.doSomething();
}
}
总结
中介者模式的优点
- 降低耦合度:
- 对象之间不再直接依赖,而是通过中介者进行通信。
- 每个对象只需知道中介者,而不需要知道其他对象的存在。
- 集中管理交互逻辑:
- 对象间的交互逻辑集中在中介者中,避免了逻辑分散。
- 修改交互逻辑时,只需修改中介者,而不需要修改各个对象。
- 提高系统的可扩展性:
- 新增对象时,只需修改中介者,而不需要修改现有对象。
- 系统的扩展性和灵活性得到提升。
- 简化代码结构:
- 对象间的依赖关系变得清晰,代码更易于理解和维护。
- 增强可维护性:
- 由于交互逻辑集中在中介者中,调试和维护更加方便。
中介者模式的缺点
- 中介者可能变得复杂:
- 如果对象间交互复杂,中介者可能会变得庞大且难以维护。
- 中介者承担了过多的职责,可能违反单一职责原则。
- 性能瓶颈:
- 所有交互都通过中介者进行,可能导致中介者成为性能瓶颈。
- 过度集中化:
- 中介者集中了所有交互逻辑,可能导致系统过度依赖中介者,难以拆分或重构。
中介者模式的适用场景
- 对象间交互复杂:
- 当多个对象之间存在复杂的交互关系,直接依赖会导致耦合度过高时,适合使用中介者模式。
- 需要集中管理交互逻辑:
- 当对象间的交互逻辑分散在各个对象中,难以维护时,可以通过中介者集中管理。
- 需要解耦对象间的依赖:
- 当对象之间需要解耦,避免直接依赖时,中介者模式是一个很好的选择。
- 适用于事件驱动系统:
- 在事件驱动系统中,中介者可以充当事件分发器,集中管理事件的传递和处理。
- GUI 开发:
- 在 GUI 开发中,中介者模式常用于管理组件间的交互,例如按钮点击、输入框变化等。
- 多对多通信场景:
- 当多个对象需要相互通信,且通信关系复杂时,中介者模式可以简化通信逻辑。
参考
黑马程序员Java设计模式详解, 23种Java设计模式(图解+框架源码分析+实战)_哔哩哔哩_bilibili
热门推荐
路特斯等车企实现RNC量产,汽车主动降噪技术迎来突破
二十七年,桃花心木般的爱情
从广三铁路起点到网红打卡地,石围塘火车站的百年新生
距今4300年大变局:气候变化与文明转型
玄空择日法:传统风水学的现代应用
张深鲤的玄空风水:传统智慧与现代科学的对话
中药配伍智慧:科学证实“君臣佐使”增效减毒
常用中药材麻黄:治疗风寒感冒、咳喘的良药
华法林患者的饮食禁忌:这些食物要当心
海口云洞图书馆等你来:海南三大免费露营地全攻略
专家解读:低GI饮食法助糖尿病患者稳定血糖
肥城美食打卡攻略:从烧饼到羊肉汤
长途旅行小腿酸胀?最容易忽视的致命危机!
白噪音助眠法:科学应对高考考前失眠问题
分级诊疗+智能医疗:医院高效应对大规模伤员的新路径
五年级语文期中复习:高效选择题攻略
南科大团队发现乙酰化修饰调控植物自噬新机制
刘欢健康危机:音乐还能继续吗?
刘欢确诊“不死癌症”15年:从舞台之巅到拄拐行走
刘欢确诊“不死癌症”,医生提醒:这种习惯最伤身
澳洲“国宝鱼”墨瑞鳕在中国走红,年产2000万尾满足高端市场需求
鳗鱼营养价值超普通鱼类60倍,专家建议慎食野生海鳗
体德智训发布:10种高效增肌的徒手训练法
香港公共交通全攻略:地铁巴士使用指南
香港两日游必打卡:迪士尼、维港、太平山顶
手指发胀别轻视:可能是疾病征兆,3种方法助你缓解
职场社交礼仪培训,让你更受欢迎
AI驱动的数据分析:利用自然语言实现数据查询到可视化呈现
如何用AI查数据库
妈妈鞋真的能拯救老母亲的脚?