【设计模式】中介者模式

中介者模式(Mediator Pattern)

概念:

· 一种行为型设计模式;

· 通过一个中介者对象来封装对象之间的交互;

· 各个对象之间不再直接引用或通信,而是通过中介者转发消息或协调行为;

· 核心思想是所有的对象都通过一个中介者进行交互,避免对象之间形成网状的依赖关系;

UML结构:

复制代码
                +----------------+
                |   IMediator    |   <<interface>>
                +----------------+
                | +Send(msg, c)  |
                | +Register(c)   |
                +----------------+
                        ^
                        |
            +------------------------+
            |   ConcreteMediator     |
            +------------------------+
            | -colleagues: List<Colleague> |
            +------------------------+
            | +Send(msg, c)          |
            | +Register(c)           |
            +------------------------+
                        |
         ---------------------------------
         |               |               |
+----------------+ +----------------+ +----------------+
|   Colleague    | |   Colleague    | |   Colleague    |
+----------------+ +----------------+ +----------------+
| -mediator      | | -mediator      | | -mediator      |
| +Send(msg)     | | +Send(msg)     | | +Send(msg)     |
| +Receive(msg)  | | +Receive(msg)  | | +Receive(msg)  |
+----------------+ +----------------+ +----------------+
        ^                ^                  ^
        |                |                  |
+----------------+ +----------------+ +----------------+
| ConcreteUser   | | ConcreteUser   | | ConcreteUser   |
+----------------+ +----------------+ +----------------+
| +Receive(msg)  | | +Receive(msg)  | | +Receive(msg)  |
+----------------+ +----------------+ +----------------+

代码示例:

cs 复制代码
/// <summary>
/// 中介者接口
/// </summary>
public interface IMediator
{
    void Send(string message, Colleague colleague);
}

/// <summary>
/// 抽象的同事类
/// </summary>
public abstract class Colleague
{
    protected IMediator mediator;

    public string Name { get; private set; }

    public Colleague(string name, IMediator mediator)
    {
        this.Name = name;
        this.mediator = mediator;
    }

    public void Send(string message)
    {
        mediator.Send(message, this);
    }

    public abstract void Receive(string message);
}

/// <summary>
/// 具体同事类
/// </summary>
public class ConcreteColleague : Colleague
{
    public ConcreteColleague(string name, IMediator mediator) : base(name, mediator) { }

    public override void Receive(string message)
    {
        Console.WrileLine($"{Name} 收到消息: {message}");
    }
}

/// <summary>
/// 具体中介者
/// </summary>
public class ConcreteMediator : IMediator
{
    private List<Colleague> colleagueList = new();

    public void Register(Colleague colleague)
    {
        if (!colleague.Contains(Colleague))
            colleagueList.Add(colleague);
    }

    public void Send(string message, Colleague sender)
    {
        foreach (var colleague in colleagueList)
        {
            if (colleague != sender)
                colleague.Receive($"{sender.Name} 说: {message}");
        }
    }
}

/// <summary>
/// 客户端
/// </summary>
public class Client
{
    public static void Main()
    {
        ConcreteMediator mediator = new ConcreteMediator();

        Colleague alice = new ConcreteColleague("Alice", mediator);
        Colleague bob = new ConcreteColleague("Bob", mediator);
        Colleague charlie = new ConcreteColleague("Charlie", mediator);

        mediator.Register(alice);
        mediator.Register(bob);
        mediator.Register(charlie);

        alice.Send("大家好,我是Alice");
        bob.Send("你好 Alice,我是Bob");
        charlie.Send("你们好,我是Charlie");
    }
}

特点:
优点:

· 降低耦合:同事类之间不依赖其他类,只依赖中介者;

· 系统中的对象复杂交互都在中介者中,这便于统一管理

· 易于拓展和维护:添加新同事或修改逻辑时只需要修改中介者即可
缺点:

· 中介者的存在增加了系统的复杂度

· 中介者又需要维护同事,又需要处理业务逻辑,违背了单一职责原则

适用场景:

· 对象之间通信复杂且紧密的场景

· 希望通过集中管理减少类之间的耦合

· 希望提供系统的可维护性和可拓展性

举例场景:

· 聊天室系统:用户之间不直接发送消息,而是通过中介者进行转发;

· 飞机调度系统:每架飞机不直接和其他飞机通信,而是通过 空中交通管制中心协调起降;

· GUI 界面控件:窗口或对话框类 进行交互,而不是直接相互调用事件处理;

相关推荐
wling03011 天前
vasp虚频计算-python脚本
开发语言·windows·python·vasp计算
郝学胜-神的一滴1 天前
Qt 高级编程 040:按钮悬浮弹出滑块弹窗的完整攻略
开发语言·c++·qt·软件工程·用户界面
xrandzj1 天前
Python面向对象编程入门:类、实例、初始化与封装实践
开发语言·python
DLYSB_1 天前
API 网关流量洪峰与突发 CC 攻击:我用 Go 写了个“现场物理防御哨兵”,把故障响应压缩到秒级
开发语言·后端·golang·报警灯
雨田言炎1 天前
四、关于Qt项目需要知道的
开发语言·笔记·qt
猿长大人1 天前
C# | JSON 序列化中的多态接口处理:基于 Attribute 实现精准 $type 控制
c#·json
程序喵大人1 天前
【C++进阶】STL算法与函数对象 - 02 sort为什么需要随机访问迭代器
开发语言·c++·算法
SomeB1oody1 天前
【RustyML入门】2.6. 线性判别分析
开发语言·后端·机器学习·rust·教程
用户昵称1001 天前
C/C++编程-工程实践-本地存储log的工程意义
c语言·开发语言
吹什么轩1 天前
c++复习:map和set的使用
开发语言·c++