• 行为类模式(五):中介者(Mediator)


    定义

    定义一个中介对象来封装系列对象之间的交互。中介者使各个对象不需要显示地相互引用,从而使其耦合性松散,而且可以独立地改变他们之间的交互。

    试想一下,如果多个类之间相互都有引用,那么当其中一个类修改时,势必导致所有相关联的类都需要修改,如果引入一个中介类来管理所有类的交互,即所有类都通过中介类和其它类交互,则可以大大降低多个类之间的耦合;中介对象主要是用来封装行为的,行为的参与者就是那些对象,但是通过中介者,这些对象不用相互知道。

    UML

    优点

    1. 降低了系统对象之间的耦合性,使得对象易于独立的被复用;
    2. 提高系统的灵活性,使得系统易于扩展和维护;
    3. 可以让对象之间传递的消息变得简单而且大幅减少。

    缺点

    1. 如果设计不当,中介者对象本身会变得过于复杂;
    2. 因为中介承担了较多的责任,所以一旦这个中介对象出现了问题,那么整个系统就会受到重大的影响。

    应用场景

    1. 一组定义良好的对象,现在要进行复杂的通信。
    2. 定制一个分布在多个类中的行为,而又不想生成太多的子类。

    示例

    考虑一种简单的情况只有两个类A和B,类中各有一个数字,并且要保证类B中的数字永远是类A中数字的100倍。也就是说,当修改类A的数时,将这个数字乘以100赋给类B,而修改类B时,要将数除以100赋给类A。

    Java

      1 public class Main
      2 {
      3     public static void main(String[] args)
      4     {
      5         AbstractColleague collA = new ColleagueA();
      6         AbstractColleague collB = new ColleagueB();
      7 
      8         AbstractMediator am = new Mediator(collA, collB);
      9 
     10         System.out.println("==========通过设置A影响B==========");
     11         collA.setNumber(1000, am);
     12         System.out.println("collA的number值为:" + collA.getNumber());
     13         System.out.println("collB的number值为A的100倍:" + collB.getNumber());
     14 
     15         System.out.println("==========通过设置B影响A==========");
     16         collB.setNumber(1000, am);
     17         System.out.println("collB的number值为:" + collB.getNumber());
     18         System.out.println("collA的number值为B的0.01倍:" + collA.getNumber());
     19     }
     20 
     21     /**
     22      * 中介类基类
     23      */
     24     public static abstract class AbstractMediator
     25     {
     26         protected AbstractColleague A;
     27         protected AbstractColleague B;
     28 
     29         public AbstractMediator(AbstractColleague a, AbstractColleague b)
     30         {
     31             A = a;
     32             B = b;
     33         }
     34 
     35         public abstract void AaffectB();
     36 
     37         public abstract void BaffectA();
     38     }
     39 
     40     /**
     41      * 同事类基类
     42      */
     43     public static abstract class AbstractColleague
     44     {
     45         protected int number;
     46 
     47         public int getNumber()
     48         {
     49             return number;
     50         }
     51 
     52         public void setNumber(int number)
     53         {
     54             this.number = number;
     55         }
     56 
     57         //注意这里的参数不再是同事类,而是一个中介者
     58         public abstract void setNumber(int number, AbstractMediator am);
     59     }
     60 
     61     /**
     62      * 同事类A
     63      */
     64     public static class ColleagueA extends AbstractColleague
     65     {
     66 
     67         public void setNumber(int number, AbstractMediator am)
     68         {
     69             this.number = number;
     70             am.AaffectB();
     71         }
     72     }
     73 
     74     /**
     75      * 同事类B
     76      */
     77     public static class ColleagueB extends AbstractColleague
     78     {
     79         @Override
     80         public void setNumber(int number, AbstractMediator am)
     81         {
     82             this.number = number;
     83             am.BaffectA();
     84         }
     85     }
     86 
     87     /**
     88      * 中介实现类
     89      */
     90     public static class Mediator extends AbstractMediator
     91     {
     92         public Mediator(AbstractColleague a, AbstractColleague b)
     93         {
     94             super(a, b);
     95         }
     96 
     97         //处理A对B的影响
     98         public void AaffectB()
     99         {
    100             int number = A.getNumber();
    101             B.setNumber(number * 100);
    102         }
    103 
    104         //处理B对A的影响
    105         public void BaffectA()
    106         {
    107             int number = B.getNumber();
    108             A.setNumber(number / 100);
    109         }
    110     }
    111 }
    View Code
  • 相关阅读:
    后台点赞 接口
    三表联查
    后台投票 接口
    MSXML insertBefore(IXMLDOMNode *newChild, VARIANT refChild) 传参
    WTL中菜单栏及工具栏项状态改变应注意的地方
    使用WTL的消息反射封装CEdit实现监听控件文本改变事件
    修改字体
    CEdit实现文本换行
    VC中获取窗口控件相对客户区的坐标
    关闭HTC手机充电时屏幕一直亮着绿色电池的办法
  • 原文地址:https://www.cnblogs.com/hammerc/p/4743804.html
Copyright © 2020-2023  润新知