中介者模式(Mediator Pattern)详解
文章目录
- 1. 中介者模式概述
- 1.1 定义
- 1.2 基本思想
- 2. 中介者模式的结构
- 3. 中介者模式的UML类图
- 4. 中介者模式的工作原理
- 5. Java实现示例
- 5.1 基本实现示例
- 5.2 飞机空中交通控制示例
- 5.3 GUI应用中的中介者模式
- 6. 中介者模式的优缺点
- 6.1 优点
- 6.2 缺点
- 7. 中介者模式的适用场景
- 8. 中介者模式在框架中的应用
- 8.1 Java Swing中的应用
- 8.2 Spring框架中的应用
- 9. 中介者模式与其他设计模式的区别与联系
- 9.1 中介者模式与观察者模式
- 9.2 中介者模式与外观模式
- 9.3 中介者模式与命令模式
- 10. 实战案例:智能家居控制系统
- 11. 总结
1. 中介者模式概述
1.1 定义
中介者模式是一种行为型设计模式,它通过一个中介对象来封装一系列对象之间的交互。中介者使各个对象不需要显式地相互引用,从而使其耦合松散,而且可以独立地改变它们之间的交互。
1.2 基本思想
中介者模式的核心思想是:
- 将对象间的复杂交互关系转换为星形结构
- 对象之间不再直接通信,而是通过中介者对象协调完成
- 减少了对象间的相互依赖,降低了系统的耦合度
2. 中介者模式的结构
中介者模式包含以下角色:
- 抽象中介者(Mediator):定义了同事对象到中介者对象的接口
- 具体中介者(ConcreteMediator):实现抽象中介者的方法,协调各个同事对象来实现协作行为
- 抽象同事类(Colleague):定义了同事类的接口,保存对中介者对象的引用
- 具体同事类(ConcreteColleague):实现抽象同事类的方法,每个具体同事类只知道自己的行为,而不了解其他同事类的情况
3. 中介者模式的UML类图
┌───────────────┐ ┌───────────────────┐
│ <<interface>> │ │ Colleague │
│ Mediator │◄────────├───────────────────┤
├───────────────┤ │ -mediator:Mediator│
│+notifyColleague()│ │ +setMediator() │
└───────┬───────┘ │ +send() ││ └─────────┬─────────┘│ ││ │
┌───────▼───────┐ ┌───────────┴─────────────┐
│ConcreteMediator│ │ │
├───────────────┤ │ │
│-colleagues │ │ │
│+notifyColleague()│ │ │
└───────────────┘ ┌───▼───────────┐ ┌───────▼─────────┐│ConcreteColleague1│ │ConcreteColleague2│├─────────────────┤ ├─────────────────┤│+send() │ │+send() ││+receive() │ │+receive() │└─────────────────┘ └─────────────────┘
4. 中介者模式的工作原理
- 各个同事对象持有对中介者对象的引用
- 当一个同事对象需要与其他同事对象交互时,它通过中介者对象发送消息
- 中介者对象接收到消息后,决定将消息转发给哪些同事对象
- 其他同事对象接收到中介者对象转发的消息,并作出响应
- 整个交互过程中,各个同事对象只与中介者对象交互,而不直接与其他同事对象通信
5. Java实现示例
5.1 基本实现示例
下面是一个简单的中介者模式实现示例,模拟用户之间通过聊天室(中介者)进行交流:
import java.util.ArrayList;
import java.util.List;// 抽象中介者
interface ChatMediator {void sendMessage(String message, User user);void addUser(User user);
}// 抽象同事类
abstract class User {protected ChatMediator mediator;protected String name;public User(ChatMediator mediator, String name) {this.mediator = mediator;this.name = name;}public abstract void send(String message);public abstract void receive(String message);
}// 具体中介者
class ChatRoom implements ChatMediator {private List<User> users;public ChatRoom() {this.users = new ArrayList<>();}@Overridepublic void addUser(User user) {this.users.add(user);}@Overridepublic void sendMessage(String message, User user) {// 将消息发送给除了发送者之外的所有用户for (User u : users) {if (u != user) {u.receive(message);}}}
}// 具体同事类
class ChatUser extends User {public ChatUser(ChatMediator mediator, String name) {super(mediator, name);}@Overridepublic void send(String message) {System.out.println(this.name + " 发送消息: " + message);mediator.sendMessage(message, this);}@Overridepublic void receive(String message) {System.out.println(this.name + " 收到消息: " + message);}
}// 客户端代码
public class MediatorPatternDemo {public static void main(String[] args) {ChatMediator chatRoom = new ChatRoom();User user1 = new ChatUser(chatRoom, "张三");User user2 = new ChatUser(chatRoom, "李四");User user3 = new ChatUser(chatRoom, "王五");chatRoom.addUser(user1);chatRoom.addUser(user2);chatRoom.addUser(user3);user1.send("大家好!");System.out.println("---------");user2.send("张三你好!");}
}
5.2 飞机空中交通控制示例
下面是一个模拟飞机着陆控制塔作为中介者协调多架飞机的例子:
import java.util.ArrayList;
import java.util.List;// 抽象中介者
interface AirTrafficControlMediator {void registerFlight(Flight flight);void registerRunway(Runway runway);boolean isRunwayAvailable();void setRunwayStatus(boolean status);void notifyFlightLanded();
}// 抽象同事类
interface Command {void execute();
}// 抽象飞行器
abstract class Flight {protected AirTrafficControlMediator mediator;public Flight(AirTrafficControlMediator mediator) {this.mediator = mediator;}public abstract void land();
}// 机场跑道类
class Runway {private AirTrafficControlMediator mediator;public Runway(AirTrafficControlMediator mediator) {this.mediator = mediator;mediator.registerRunway(this);}public void setStatus(boolean status) {mediator.setRunwayStatus(status);}
}// 具体中介者
class AirTrafficControlTower implements AirTrafficControlMediator {private Flight flight;private Runway runway;private boolean runwayAvailable;public AirTrafficControlTower() {runwayAvailable = true;}@Overridepublic void registerFlight(Flight flight) {this.flight = flight;}@Overridepublic void registerRunway(Runway runway) {this.runway = runway;}@Overridepublic boolean isRunwayAvailable() {return runwayAvailable;}@Overridepublic void setRunwayStatus(boolean status) {runwayAvailable = status;}@Overridepublic void notifyFlightLanded() {System.out.println("跑道现在可用");setRunwayStatus(true);}
}// 具体飞行器:航班
class CommercialFlight extends Flight {private String flightNumber;public CommercialFlight(AirTrafficControlMediator mediator, String flightNumber) {super(mediator);this.flightNumber = flightNumber;mediator.registerFlight(this);}@Overridepublic void land() {if (mediator.isRunwayAvailable()) {System.out.println("商业航班 " + flightNumber + " 成功着陆。");mediator.setRunwayStatus(false);// 模拟飞机着陆后离开跑道new Thread(() -> {try {Thread.sleep(3000); // 假设飞机需要3秒离开跑道mediator.notifyFlightLanded();} catch (InterruptedException e) {e.printStackTrace();