设计模式第15篇:观察者模式
一.观察者模式介绍
观察者设计模式是一种行为设计模式,该模式中观察者为observer,被观察的对象称为subject。当我们对一个对象(subject对象)的状态感兴趣并且当这个对象的状态改变时观察它的对象(observer)将被通知时,应该考虑观察者设计模式,它处理的是一种一对多的关系,典型应用如消息订阅。
二.观察者模式代码用例
1.被观察者接口Subject
/**被观察者对象接口*/ interface Subject{ /** * 注册观察者(订阅者) * @param observer 观察者 */ void register(Observer observer); /** * 删除观察者(订阅者) * @param observer 观察者 */ void unRegister(Observer observer); /** * 通知所有观察者 */ void notifyObservers(); /** * 通知观察者的具体行为 * @return 通知观察者的具体消息对象 */ Object getUpdate(); }
2.被观察对象实例MessageServer
/** * 消息服务器(一个被观察的对象实例) */ class MessageServer implements Subject{ /** * 用于存储所有观察者的集合 */ private List<Observer> observerList; /** * 通知观察者的具体信息 */ private String message; /** * 被观察者对象标识,false表示状态未改变 */ private boolean flag = false; public MessageServer(){ this.observerList = new ArrayList<>(16); } @Override public synchronized void register(Observer observer) { if(!observerList.contains(observer)) observerList.add(observer); } @Override public synchronized void unRegister(Observer observer) { if(observerList.contains(observer)) observerList.remove(observer); } @Override public void notifyObservers() { if(!flag) return; for(Observer ob:observerList){ ob.update(); } this.flag=false; } @Override public Object getUpdate() { return this.message; } public void postMessage(String message){ System.out.println("post messages to MessageServer: "+message); this.message=message; this.flag=true; notifyObservers(); } }
3.观察者接口
/** * 观察者对象接口 */ interface Observer{ /** * 观察者收到信息后作出的动作 */ void update(); /** * 将观察者绑定到被观察者对象上 * @param subject 被观察者对象 */ void setSubject(Subject subject); }
4.观察者对象实例
/** * 消息订阅者对象 */ class MessageSubscriber implements Observer{ /** * 观察者名字 */ private String name; /** * 被订阅对象 */ private Subject subject; public MessageSubscriber(String name,Subject subject){ this.name=name; setSubject(subject); } @Override public void update() { String message=(String)subject.getUpdate(); if(message==null||message.equals("")){ System.out.println(name +"no messages to receive"); }else{ System.out.println(name +" receive the new message:"+message); } } @Override public void setSubject(Subject subject) { this.subject=subject; } }
5.测试
public class ObserverTest { public static void main(String[] args){ MessageServer messageServer=new MessageServer(); MessageSubscriber subscriber1=new MessageSubscriber("张三",messageServer); MessageSubscriber subscriber2=new MessageSubscriber("李四",messageServer); MessageSubscriber subscriber3=new MessageSubscriber("王五",messageServer); messageServer.register(subscriber1); messageServer.register(subscriber2); messageServer.register(subscriber3); int i=0; while(i<10){ messageServer.postMessage("新的消息1"); messageServer.unRegister(subscriber2); messageServer.postMessage("新的消息2"); i++; } } }
三.观察者模式应用场景
观察者模式也被称为发布-订阅模式,主要应用在消息订阅等服务中。
jdk中用到的观察者模式:java.util.EventListener in Swing;
javax.servlet.http.HttpSessionBindingListener;
javax.servlet.http.HttpSessionAttributeListener