Qt C++设计模式->中介者模式

news/2024/10/22 10:44:04/

中介者模式(Mediator Pattern)是一种行为型设计模式,定义了一个对象用于封装一系列对象之间的交互。中介者使得对象之间不再需要显式地相互引用,减少了对象之间的依赖关系,从而使系统更加松散耦合,并且可以独立地改变对象之间的交互。

中介者模式的应用场景

中介者模式适用于当多个对象之间存在复杂的通信关系时,通过引入一个中介者对象来管理这些对象之间的交互,避免了对象之间直接相互依赖,降低系统的复杂性。常见的应用场景包括:

  1. GUI系统:在复杂的用户界面中,不同的控件(如按钮、文本框等)可能需要交互。中介者模式可以协调这些控件之间的通信,使得每个控件只与中介者交互。

  2. 聊天系统:在一个聊天室中,用户可以相互发送消息,使用中介者可以让每个用户只与中介者交互,由中介者负责消息的分发。

  3. 航空控制系统:飞机之间的通信可以通过中介者(如塔台)来进行协调,避免它们直接通信。

中介者模式的核心

中介者模式通过引入一个中介者对象来协调多个对象之间的通信。模式中的主要组成部分包括:

  1. 中介者接口(Mediator):定义了与对象交互的接口,负责通知对象并管理对象之间的交互。

  2. 具体中介者(Concrete Mediator):实现了中介者接口,负责具体的交互逻辑。

  3. 同事类(Colleague):代表参与交互的对象,它们只通过中介者来通信,不直接与其他同事对象进行交互。

中介者模式示例代码

假设我们在开发一个简化版的聊天室系统,每个用户可以向聊天室发送消息,聊天室负责将消息分发给其他用户。

1. 定义中介者接口和具体中介者

#include <QDebug>
#include <QString>
#include <QList>// 前向声明
class User;// 中介者接口
class ChatMediator {
public:virtual void sendMessage(const QString& message, User* sender) = 0;  // 发送消息方法virtual void addUser(User* user) = 0;  // 添加用户virtual ~ChatMediator() = default;
};// 同事类接口:用户
class User {
protected:ChatMediator* mediator;  // 持有中介者对象QString name;public:User(ChatMediator* mediator, const QString& name) : mediator(mediator), name(name) {}virtual void send(const QString& message) = 0;  // 发送消息virtual void receive(const QString& message) const = 0;  // 接收消息
};// 具体同事类:聊天室用户
class ChatUser : public User {
public:ChatUser(ChatMediator* mediator, const QString& name) : User(mediator, name) {}void send(const QString& message) override {qDebug() << name << "sends:" << message;mediator->sendMessage(message, this);  // 通过中介者发送消息}void receive(const QString& message) const override {qDebug() << name << "receives:" << message;}
};// 具体中介者:聊天室
class ChatRoom : public ChatMediator {
private:QList<User*> users;  // 用户列表public:void addUser(User* user) override {users.append(user);  // 添加用户到聊天室}void sendMessage(const QString& message, User* sender) override {// 遍历所有用户,将消息发送给除了发送者以外的所有用户for (User* user : users) {if (user != sender) {user->receive(message);}}}
};// 使用示例
int main() {// 创建聊天室ChatRoom* chatRoom = new ChatRoom();// 创建用户User* user1 = new ChatUser(chatRoom, "Alice");User* user2 = new ChatUser(chatRoom, "Bob");User* user3 = new ChatUser(chatRoom, "Charlie");// 将用户添加到聊天室chatRoom->addUser(user1);chatRoom->addUser(user2);chatRoom->addUser(user3);// 用户发送消息user1->send("Hello everyone!");  // 输出:Bob receives: Hello everyone!; Charlie receives: Hello everyone!user2->send("Hi Alice!");        // 输出:Alice receives: Hi Alice!; Charlie receives: Hi Alice!// 清理内存delete user1;delete user2;delete user3;delete chatRoom;return 0;
}

代码解析

  • ChatMediator接口:定义了一个用于发送消息和添加用户的中介者接口。

  • ChatRoom类:这是具体的中介者,管理聊天室的用户,并负责将消息从发送者分发给其他用户。

  • User类:这是同事类的基类,表示参与聊天的用户。用户通过中介者来发送和接收消息。

  • ChatUser类:具体的同事类,表示聊天室中的具体用户。它们只与中介者ChatRoom进行交互,而不直接与其他用户通信。

  • 客户端代码:客户端通过创建用户并将它们添加到聊天室,用户可以通过中介者发送和接收消息,而不需要直接知道其他用户的存在。

中介者模式的优点

  • 降低耦合性中介者模式消除了对象之间的直接依赖,使得同事对象只需与中介者交互,降低了系统的耦合性,提升了模块的独立性和可维护性。

  • 简化对象的通信:中介者负责管理对象之间的通信,简化了多对象之间的复杂通信逻辑。

  • 集中控制交互:中介者可以集中管理和控制对象之间的交互,便于修改和扩展交互逻辑。

中介者模式的缺点

  • 增加复杂性:中介者可能会变得过于复杂,承担过多的责任,变成一个“上帝对象”(God Object),使得维护中介者本身变得困难。

  • 中介者变得庞大:随着系统的复杂化,中介者会变得越来越大,可能导致中介者的设计难以管理。

适合使用中介者模式的情况

  • 对象之间的通信过于复杂:如果多个对象之间的交互非常复杂并且紧密耦合,使用中介者模式可以简化这些交互,并解耦各对象。

  • 需要集中管理对象的交互:当系统的交互逻辑较为复杂,并且可能会经常变化时,中介者模式提供了集中控制交互的方式。

Qt中的中介者模式应用

在Qt开发中,中介者模式可以用于处理控件之间的交互。例如,多个控件之间的状态可能需要互相影响,如按钮、文本框、复选框等。通过引入一个中介者,可以让这些控件只与中介者通信,而不是直接互相依赖,这样可以避免UI控件之间的耦合。

中介者模式还可以应用于事件处理系统中,Qt的信号与槽机制与中介者模式有相似之处:通过信号与槽的机制,信号的发送者和接收者彼此不需要知道对方的存在,类似于中介者在管理多个对象之间的交互。

总结

中介者模式通过引入一个中介者对象,将对象之间的直接交互转换为通过中介者来进行,从而降低了对象之间的耦合度。它适用于对象之间交互复杂且紧密耦合的场景,通过集中控制交互,提升了系统的可维护性和灵活性。


http://www.ppmy.cn/news/1538384.html

相关文章

前端框架对比与选择:详尽分析

1. 引言 随着互联网技术的飞速发展,前端开发技术也得到了迅猛提升。无论是大型企业还是中小型开发团队,使用前端框架来简化开发过程、提升开发效率已成为一种普遍现象。如今,市场上有众多的前端框架可供选择,如React、Vue.js、Angular等,如何在这些框架中进行选择成为了开…

牛客编程初学者入门训练——BC8 牛牛的字符菱形

BC8 牛牛的字符菱形 描述&#xff1a; 牛牛尝试用键盘读入一个字符&#xff0c;然后在屏幕上显示一个用这个字符填充的对角线长5个字符&#xff0c;倾斜放置的菱形。 输入描述&#xff1a; 输入一个char类型字符 输出描述&#xff1a; 输出一个用这个字符填充的对角线长5…

【ShuQiHere】 K-means 聚类算法详解:公式、代码与实战

&#x1f9e0; 【ShuQiHere】 &#x1f393; 目录 &#x1f4dc; K-means 简介K-means 工作原理理论基础 3.1 目标函数3.2 距离度量 K-means 算法步骤 4.1 具体代码实现 K-means 的优缺点如何选择正确的 K 值K-means 的改进与变体案例分析&#xff1a;如何使用 K-means 聚类&…

HTML,JavaScript,PHP,CSS,XML,SQL的区别和联习

HTML超文本标记语言——HyperText Markup Language&#xff09;是构成 Web 世界的一砖一瓦。它定义了网页内容的含义和结构。除 HTML 以外的其他技术则通常用来描述一个网页的表现与展示效果&#xff08;如 CSS&#xff09;&#xff0c;或功能与行为&#xff08;如 JavaScript&…

SpringBoot 集成GPT实战,超简单详细

Spring AI 介绍 在当前的AI应用开发中&#xff0c;像OpenAI这样的GPT服务提供商主要通过HTTP接口提供服务&#xff0c;这导致大部分Java开发者缺乏一种标准化的方式来接入这些强大的语言模型。Spring AI Alibaba应运而生&#xff0c;它作为Spring团队提供的一个解决方案&…

【WebGIS】Cesium:Viewer 初始化、地图加载与基础交互

Cesium 是一个功能强大、基于 WebGL 的开源三维地球引擎&#xff0c;它允许用户在浏览器中渲染高性能的三维地图和地球。本文将带领新手入门 Cesium&#xff0c;学习如何初始化 Cesium Viewer&#xff0c;加载地图和地形&#xff0c;了解地球的基础交互操作&#xff0c;并掌握如…

在Pycharm中安装Cv2

在PyCharm中安装cv2&#xff08;即OpenCV库&#xff09;&#xff0c;你可以使用pip包管理器。以下是步骤和示例代码&#xff1a; 1.打开PyCharm。 2.确保你的项目解释器已经设置。在PyCharm的右下角可以看到当前使用的解释器。 3.点击解释器名称&#xff08;通常是解释器路径…

机器学习和神经网络的研究与传统物理学的关系

机器学习和神经网络的研究与传统物理学的关系 机器学习和神经网络是现代科学研究中非常热门的领域&#xff0c;它们与传统物理学在某些方面有着密切的关系&#xff0c;在人类科学研究中相互影响和促进作用也越来越显著。 首先&#xff0c;机器学习和神经网络在物理学研究中具…