中介者模式是由GoF提出的23种软件设计模式的一种。Mediator模式是行为模式之一,Mediator模式定义:用一个中介者对象来封装一系列的对象交互。中介者使各对象不需要显式的相互引用,从而使其耦合松散,而且可以独立的改变他们之间的交互。
适用性:
1)一组对象以定义良好但是复杂的方式进行通信。产生的相互依赖关系结构混乱且难以理解。
2)一个对象引用其他很多对象并且直接与这些对象通信,导致难以复用该对象。
3)想定制一个分布在多个类的行为,而又不想生成太多的子类。
试想有这样一个场景:有一家JobMediator(可以理解为工作信息发布网站),公司可以往上面发布招聘信息。而求职者可以根据平台上发布的信息来选择自己的有意向的公司发布信息。利用中介模式我们可以通过JobMediator 来实现求职者与招聘者间的通信而避免了对象间复杂的通信。另外当有新的公司注册并且达到了某些求职者的要求的时候,我们可以给这些求职者(相当于观察着)发送有新公司注册的消息。这样可进行如下建模:
实现代码如下:
MyObserver.java
package com.houjx.observers;
public interface MyObserver {
//这个相当于java.util.Observer 接口
void update(MyObservable o, Object arg);
}
MyObervable.java
package com.houjx.observers;
import java.util.Vector;
import com.houjx.members.*;
public class MyObservable {
//相当于java.util.Observable 类
private boolean changed = false;
private Vector obs;
//创建被观察者时就创建一个它持有的观察者列表,注意,这个列表是需要同步的。
public MyObservable() {
obs = new Vector();
}
/**
* 添加观察者到观察者列表中去
*/
public synchronized void addObserver(MyObserver o) {
if (o == null)
throw new NullPointerException();
if (!obs.contains(o)) {
obs.addElement(o);
}
}
/**
* 删除一个观察者
*/
public synchronized void deleteObserver(MyObserver o) {
obs.removeElement(o);
}
/**
* 通知操作,即被观察者发生变化,通知对应的观察者进行事先设定的操作,不传参数的通知方法
*/
public void notifyObservers() {
notifyObservers(null);
}
/**
* 与上面的那个通知方法不同的是,这个方法接受一个参数,这个参数一直传到观察者里,以供观察者使用
*/
public void notifyObservers(Object arg) {
Object[] arrLocal;
synchronized (this) {
if (!changed)
return;
arrLocal = obs.toArray();
clearChanged();
}
for (int i = arrLocal.length-1; i>=0; i--)
if(((Students)arrLocal[i]).isOk(((Company)arg).getOfferSalary())){
//遍历观察者(已注册的学生)看公司的条件是否达到学生的要求,满足则向学生发送信息。
//这里简单起见只是以工资为标准的。
((MyObserver)arrLocal[i]).update(this, arg);
}
}
private void clearChanged() {
// TODO Auto-generated method stub
changed=false;
}
public void setChanged(){
changed=true;
}
}
Mediator.java
package com.houjx.members;
public interface Mediator {
void comRegister(Company com);//公司注册
void stuRegister(Students stu);//学生注册
void sendMes(Students s,String comName,String info);//实现学生向公司发送求职意向信息
}
Students.java
package com.houjx.members;
public class Students {
private String name;
private double exSalary;//渴望工资
private Mediator jobMediator;//保存注册的中介对象
public void sendMes(String comName,String info){
//学生向公司发送求职意向信息
jobMediator.sendMes(this,comName,info);
}
public boolean isOk(double offerSalary){
//判断工资条件是否符合求职者要求
return offerSalary>exSalary;
}
public String getName() {
return name;
}
public void setName(String name) {
this.name = name;
}
public double getExSalary() {
return exSalary;
}
public void setExSalary(double exSalary) {
this.exSalary = exSalary;
}
public Mediator getJobMediator() {
return jobMediator;
}
public void setMediator(Mediator jobMediator) {
this.jobMediator = jobMediator;
}
}
Company.java
package com.houjx.members;
public class Company {
private JobMediator jobMediator;
private String name;
private double offerSalary;
public JobMediator getJobMediator() {
return jobMediator;
}
public void setJobMediator(JobMediator jobMediator) {
this.jobMediator = jobMediator;
}
public String getName() {
return name;
}
public void setName(String name) {
this.name = name;
}
public double getOfferSalary() {
return offerSalary;
}
public void setOfferSalary(double offerSalary) {
this.offerSalary = offerSalary;
}
public void receive(Students s,String info){
System.out.println("收到学生"+s.getName()+"的信息:"+info);
}
}
CollegeStu.java
package com.houjx.members;
import com.houjx.observers.MyObservable;
import com.houjx.observers.MyObserver;
public class CollegeStu extends Students implements MyObserver {
//实现Myobserver接口,作为观察者模式中的观察着
@Override
public void update(MyObservable o, Object arg) {
// TODO Auto-generated method stub
System.out.println(getName()+" 你好:新公司"+((Company)arg).getName()+" offers "+((Company)arg).getOfferSalary());
this.sendMes(((Company)arg).getName(), "你好,我是 "+getName()+" 对你们的公司感兴趣!!");
}
}
JobMediator.java
package com.houjx.members;
import java.util.HashMap;
import com.houjx.observers.MyObservable;
public class JobMediator extends MyObservable implements Mediator {
//实现Mediator接口作为中介者
//扩展MyObservable 类,作为观察者模式中的被观察者
HashMap comHash;
HashMap stuHash;
public JobMediator(){
comHash=new HashMap();
stuHash=new HashMap();
}
@Override
public void comRegister(Company com) {
// TODO Auto-generated method stub
if(!comHash.containsKey(com.getName())){
comHash.put(com.getName(), com);
com.setJobMediator(this);
setChanged();
notifyObservers(com);
}else{
System.out.println(" 这个用户名已经存在了~~~");
}
}
@Override
public void sendMes(Students s, String comName, String info) {
// TODO Auto-generated method stub
Company com=(Company) comHash.get(comName);
if(com!=null)
com.receive(s,info);//当被观察者上面,有新公司注册时向符合条件的求职者发送信息
}
@Override
public void stuRegister(Students stu) {
if(!stuHash.containsKey(stu.getName())){
stuHash.put(stu.getName(), stu);
stu.setMediator(this);
}else{
System.out.println(" 这个用户名已经存在了~~~");
}
}
public static void main(String []args){
JobMediator jobM=new JobMediator();
CollegeStu stu1=new CollegeStu();
CollegeStu stu2=new CollegeStu();
stu1.setExSalary(2000.5);
stu1.setName("zhansan");
jobM.addObserver(stu1);
jobM.stuRegister(stu1);
stu2.setExSalary(1000.5);
stu2.setName("lisi");
jobM.addObserver(stu2);
jobM.stuRegister(stu2);
Company com=new Company();
com.setName("Oracle");
com.setOfferSalary(1985);
jobM.comRegister(com);
//Company com=new Company();
com.setName("HP");
com.setOfferSalary(3000);
jobM.comRegister(com);
}
}
运行结果:
lisi 你好:新公司Oracle offers 1985.0
收到学生lisi的信息:你好,我是 lisi 对你们的公司感兴趣!!
lisi 你好:新公司HP offers 3000.0
收到学生lisi的信息:你好,我是 lisi 对你们的公司感兴趣!!
zhansan 你好:新公司HP offers 3000.0
收到学生zhansan的信息:你好,我是 zhansan 对你们的公司感兴趣!!