一、引言
中介者模式(Mediator Pattern)是一种行为型设计模式,它通过一个中介对象封装一系列的对象交互。中介者模式使得各对象不需要显式地相互引用,从而使其耦合松散,同时也可以独立地改变它们之间的交互。此模式常用于处理复杂的对象之间的通信,以及实现对象之间的解耦。
二、使用场景
-
困难的对象间交互:当多个对象之间存在复杂的相互依赖关系时,使用中介者模式能够简化对象之间的沟通,从而更易于维护和扩展。
-
解耦关系:在需要消除对象之间直接的连接,提高代码模块化的场景,促进各种组件之间更清晰的交互。
-
集中控制:当需要集中管理多个组件并协调它们的行为时,可以使用中介者模式实现控制,避免每个组件之间直接交互。
-
消息传递和通信:在需要在多个对象之间传递消息的场景中,通过中介者简化对象之间的信息传递。
三、模式分类
- 标准中介者:通过具体中介者类来协调不同具体参与者之间的交互。
- 事件驱动中介者:中介者根据已发出的事件进行命令分发,允许参与者监听并响应事件。
四、优缺点
优点
- 降低耦合度:中介者模式减轻了对象之间的相互联系,使得对象之间的关系更加清晰。
- 增强独立性和灵活性:通过改变中介者的实现而不需要改变内部的交互逻辑,提高了系统的扩展性和灵活性。
- 集中控制:所有的交互都由中介者协调,减少了多到多关系的复杂性。
缺点
- 单点故障:通过中介者集中所有协调逻辑可能为整个系统带来单点故障,如果中介者出现问题,整个系统通信可能受到影响。
- 中介者复杂性:中介者复杂度可能随系统扩展而增加,导致其职责变得不明确或管理困难。
- 性能问题:中介者层增加了额外的调用层次,可能会影响整体性能,尤其是在历史深厚的对象交互关系中。
五、代码示例
以下是中介者模式的 C++ 实现示例。
#include <iostream>
#include <string>
#include <unordered_map>
#include <memory>
//==================== 前向声明 ====================//
class Mediator;
//==================== 同事类 ====================//
class Colleague : public std::enable_shared_from_this<Colleague> {
protected:
std::weak_ptr<Mediator> mediator_; // 弱引用,防止循环持有
std::string id_; // 同事唯一标识
public:
explicit Colleague(std::string id) : id_(std::move(id)) {}
virtual ~Colleague() = default;
void setMediator(std::shared_ptr<Mediator> m) { mediator_ = m; }
const std::string& id() const { return id_; }
virtual void send(const std::string& to, const std::string& msg) = 0;
virtual void receive(const std::string& from, const std::string& msg) = 0;
};
//==================== 中介者接口 ====================//
class Mediator : public std::enable_shared_from_this<Mediator> {
public:
virtual void registerColleague(std::shared_ptr<Colleague> colleague) = 0;
virtual void forward(const std::string& from,
const std::string& to,
const std::string& msg) = 0;
virtual ~Mediator() = default;
};
//==================== 具体中介者 ====================//
class ConcreteMediator : public Mediator {
std::unordered_map<std::string, std::weak_ptr<Colleague>> colleagues_;
public:
void registerColleague(std::shared_ptr<Colleague> colleague) override {
colleagues_.emplace(colleague->id(), colleague);
colleague->setMediator(shared_from_this());
}
void forward(const std::string& from,
const std::string& to,
const std::string& msg) override {
auto it = colleagues_.find(to);
if (it == colleagues_.end() || it->second.expired()) {
std::cout << "[Mediator] Unknown or expired recipient: " << to << "\n";
return;
}
if (auto c = it->second.lock())
c->receive(from, msg);
}
};
//==================== 具体同事类 ====================//
class ConcreteColleague : public Colleague {
public:
using Colleague::Colleague; // 继承构造函数
void send(const std::string& to, const std::string& msg) override {
if (auto m = mediator_.lock()) {
std::cout << "Colleague [" << id_ << "] sending to [" << to << "]: "
<< msg << "\n";
m->forward(id_, to, msg);
}
}
void receive(const std::string& from, const std::string& msg) override {
std::cout << "Colleague [" << id_ << "] received from [" << from << "]: "
<< msg << "\n";
}
};
int main() {
// 创建中介者
auto mediator = std::make_shared<ConcreteMediator>();
// 创建同事
auto alice = std::make_shared<ConcreteColleague>("Alice");
auto bob = std::make_shared<ConcreteColleague>("Bob");
auto carol = std::make_shared<ConcreteColleague>("Carol");
// 注册到中介者
mediator->registerColleague(alice);
mediator->registerColleague(bob);
mediator->registerColleague(carol);
// 发送消息
alice->send("Bob", "Hello Bob!");
bob->send("Carol", "Hi Carol!");
carol->send("Alice", "Good morning, Alice!");
// 向一个不存在的同事发消息
bob->send("Dave", "Anyone there?");
return 0;
}
代码解析
-
Mediator 接口:定义了中介者接口,包括发送方法
send()
,用于转发消息。 -
Colleague 基类:代表同事类的基类,具备发送和接收消息的能力,同时持有对中介者的引用。
-
ConcreteColleagueA 和 ConcreteColleagueB:具体同事类,分别实现发送和接收消息的逻辑,并通过中介者发送消息。
-
ConcreteMediator:具体中介者类,持有两个具体同事类的引用,并实现
send()
方法以监管并转发同事间的消息。 -
main():首先创建同事实例和中介者实例,然后通过同事类发消息;当收到消息后将消息转发给对应同事,最后清理资源。
六、模式总结
中介者模式是处理复杂对象交互关系的有效方式,通过中介者将对象间的直接交互转为间接,使得对象间关系的变化对其他对象影响大幅减少,提升了系统可维护性和可扩展性。适合用于需要保持对象间松耦合的交互系统,但是当引入中介者后,维护中介者的复杂性及对系统性能的影响需加以考虑。因此,在设计时应根据特定情境平衡利弊,有效利用中介者模式提升系统的灵活性和效率。
没有回复内容