目录
场景
思考
解决思路
模式讲解
调用示意图
中介者模式的优缺点
中介者模式的本质
何时选用
场景
如果没有主板,电脑各个配件怎么交互呢?
有些配件接口不同,必须把数据接口进行转换才能匹配上,无敌复杂。
有了主板之后就是下面这个样子
思考
软件开发中针对,内部复杂的我们可以找一个中介者,让中介者去处理这些事情。
解决思路
白话解析:
1.分为中介者和同事两个层级。同事们都和我交互,而我知道怎么把同事的交互跟别人的串联起来,但单个同事你不用管我是怎么跟人交互的,你做好自己的就可以了。
2.同事在处理完自己的事情后,你得告诉中介者你做了改变,让我心里有数,不能自己想做什么做什么,闷头干大事不交流。
模式讲解
结构图
代码示例:
Mediator
package day09中介者模式;/*** 中介者对象的接口*/
public interface Mediator {/*** 同事对象在自身改变的时候来通知中介者的方法,* 让中介者去负责相应的与其他同事对象的交互* @param colleague 同事对象自身,好让中介者对象通过对象实例去获取同事对象的状态*/public void changed(Colleague colleague);
}
ConcreteMediator
package day09中介者模式;import day09中介者模式.同事.CDDriver;
import day09中介者模式.同事.CPU;
import day09中介者模式.同事.SoundCard;
import day09中介者模式.同事.VideoCard;/*** 相当于主板,实现中介者对象*/
public class MediatorImpl implements Mediator {/*** 需要知道交互的同时类-光驱类*/private CDDriver cdDriver = null;/*** 需要知道交互的同时类-CPU类*/private CPU cpu = null;/*** 需要知道交互的同时类-显卡类*/private VideoCard videoCard = null;/*** 需要知道交互的同时类-声卡类*/private SoundCard soundCard = null;/*** 方法重写** @param colleague 同事对象自身,好让中介者对象通过对象实例去获取同事对象的状态*/@Overridepublic void changed(Colleague colleague) {if (colleague == cdDriver) {// 表示光驱读取数据了this.opeCDDriverReadData((CDDriver) colleague);} else if (colleague == cpu) {// 表示CPU处理完了this.opeCPU((CPU) colleague);}}/*** 处理光驱读取数据以后与其他对象的交互* @param cd 光驱同事对象*/private void opeCDDriverReadData(CDDriver cd) {//1.先获取光驱读取的数据String data = cd.getData();//2.把这些数据传递给CPU进行处理this.cpu.executeData(data);}/*** 处理CPU处理完数据后与其他对象的交互* @param cpu*/private void opeCPU(CPU cpu) {//1.先获取CPU处理后的数据String videoData = cpu.getVideoData();String soundData = cpu.getSoundData();//2.把这些数据传递给显卡和声卡展示出来this.videoCard.showData(videoData);this.soundCard.soundData(soundData);}public CDDriver getCdDriver() {return cdDriver;}public void setCdDriver(CDDriver cdDriver) {this.cdDriver = cdDriver;}public CPU getCpu() {return cpu;}public void setCpu(CPU cpu) {this.cpu = cpu;}public VideoCard getVideoCard() {return videoCard;}public void setVideoCard(VideoCard videoCard) {this.videoCard = videoCard;}public SoundCard getSoundCard() {return soundCard;}public void setSoundCard(SoundCard soundCard) {this.soundCard = soundCard;}}
Colleague,我这里定义成抽象父类
package day09中介者模式;/*** 所有同事的抽象父类的定义*/
public abstract class Colleague {/*** 持有中介者对象,每一个同事都知道它的中介者对象*/private Mediator mediator;/*** 构造方法,传入中介者对象* @param mediator*/public Colleague(Mediator mediator){this.mediator = mediator;}/*** 获取当前同时类对应的中介者对象* @return*/public Mediator getMediator(){return mediator;}
}
同事子类 分别为光驱 cpu 显卡 声卡
package day09中介者模式.同事;import day09中介者模式.Colleague;
import day09中介者模式.Mediator;/*** 光驱类*/
public class CDDriver extends Colleague {public CDDriver(Mediator mediator) {super(mediator);}/*** 光驱读取出来的数据*/private String data = "";/*** 获取光驱读取出来的数据*/public String getData(){return this.data;}/*** 读取光盘*/public void readCD(){// 逗号前是视频显示的数据,逗号后是声音this.data = "设计模式,值得好好研究";// 通知主板,自己的状态发生了改变this.getMediator().changed(this);}
}
package day09中介者模式.同事;import day09中介者模式.Colleague;
import day09中介者模式.Mediator;/*** CPU类*/
public class CPU extends Colleague {public CPU(Mediator mediator) {super(mediator);}/*** 分解出来的视频数据*/private String videoData = "";/*** 分解出来的声音数据*/private String soundData = "";/*** 获取分解出来的视频数据*/public String getVideoData() {return videoData;}/*** 获取分解出来的声音数据*/public String getSoundData() {return soundData;}public void executeData(String data) {// 把数据分解开String[] split = data.split(",");this.videoData = split[0];this.soundData = split[1];// 通知主板,CPU的工作完成this.getMediator().changed(this);}
}
package day09中介者模式.同事;import day09中介者模式.Colleague;
import day09中介者模式.Mediator;/*** 显卡类*/
public class VideoCard extends Colleague {public VideoCard(Mediator mediator) {super(mediator);}/*** 显示视频数据* @param data*/public void showData(String data){System.out.println("您正观看的是:" + data);}
}
package day09中介者模式.同事;import day09中介者模式.Colleague;
import day09中介者模式.Mediator;/*** 声卡类*/
public class SoundCard extends Colleague {public SoundCard(Mediator mediator) {super(mediator);}/*** 按照声频数据发出声音* @param data*/public void soundData(String data){System.out.println("画外音:" + data);}
}
Client
package day09中介者模式;import day09中介者模式.同事.CDDriver;
import day09中介者模式.同事.CPU;
import day09中介者模式.同事.SoundCard;
import day09中介者模式.同事.VideoCard;public class Client {public static void main(String[] args) {// 1.创建中介者-主板对象MediatorImpl mediator = new MediatorImpl();// 2.创建同事类CDDriver cdDriver = new CDDriver(mediator);CPU cpu = new CPU(mediator);VideoCard videoCard = new VideoCard(mediator);SoundCard soundCard = new SoundCard(mediator);// 3.让中介者知道所有的同事mediator.setCdDriver(cdDriver);mediator.setCpu(cpu);mediator.setVideoCard(videoCard);mediator.setSoundCard(soundCard);// 4.开始看电影cdDriver.readCD();}
}
首先有一个中介者接口Mediator,其中有一个changed方法,这个方法代表同事们发生变化后要通知我,然后是MediatorImpl实现定义的接口(相当于主板,并且定义了交互方法,需要注意的是我这个主板肯定要包含cpu,显卡,声卡,驱动等同事的,不然我的信息也没法转交)
实现changed的方法,就是怎么交互,从上到下,如果传过来的是驱动的信息,怎么搞,如果传过来是cpu的信息,怎么搞。怎么判断顺序呢?
我们自己定义的,进这个方法后
this.getMediator().changed(this); 有这么一句话,就是将自身的改变后的本身告诉中介者。
然后就在进入这个方法
判断进来的是什么实体?哦,是驱动
调用第一个if执行。
然后就进入这里 executeData
CPU处理完也是要告知中介者,我完成了,剩下的交给你做吧
就进入了第二个if。
showData
soundData
客户端使用:
1.先创建中介者
2.增加同事类
3.让中介者知道所有同事 set进去
4.开始执行第一步
调用示意图
中介者模式的优缺点
中介者模式的本质
封装交互