1.概述
1.1 定义
观察者模式定义了对象之间的一对多的依赖关系,让多个观察者对象同时监听,某一个主题对象。这个主题对象在状态发生变化时,会通知所有观察者对象,使得它们能够自动更新自己。
1.2 原理
观察者的一个通俗的例子:马路上的很多的汽车和红绿灯。汽车就是观察者,红绿灯就是被观察者,即汽车观察的目标。一旦红绿灯变成红色则汽车停止;变绿色,则汽车启动。
2.类图
3.角色
1.Subject 表示抽象目标或者主题,即被观察者。一个目标可以接受任意数量的观察者观察,将其保存在一个聚集里面,同时它提供了一个接口来注册和删除观察者对象。
2.ConcreteSubject 表示具体目标,将有关状态存入各个ConcreteObserver对象中。当它的状态发生改变时,向
它的各个观察者发出通知。
3.Observer 表示抽象观察者,在一个Subject对象的状态发生改变时,为那些需要获得通知的对象定义一个更新接口。 4.ConcreteObserver 表示具体观察者,它维护一个指向ConcreteSubject对象的引用,同时储存有关状态。
4.优缺点
4.1 优点
1.实现了表示层和数据逻辑层的分离,并定义了稳定的更新消息传递机制。 4.2 缺点
1.如果一个目标对象有很多直接或间接的观察者的话,为所有的观察者通知会耗费很多时间。 2.如果在目标之间有循环依赖的话,将会触发它们之间进行循环调用,导致系统崩溃。 3.虽然观察者模式可以随时使得观察者知道所观察的对象的状态发生了改变,但是观察者模式并没有相应的机制让观察者知道
状态是怎么变化的。
5.案例
5.1 代码
1)抽象目标类
/** * 抽象目标 * @author Administrator */ public abstract class Subject { //观察者集合 private List<Observer> observerList = new ArrayList<>(); /** * 增加观察者 * @param observer */ public void attach(Observer observer) { observerList.add(observer); } /** * 删除观察者 * @param observer */ public void detach(Observer observer) { observerList.remove(observer); } /** * 通知观察者更新 */ public void notifyObserver() { for (Observer observer : observerList) { observer.update(); } } }
2)具体目标类
/** * 具体目标类 * @author Administrator * */ public class ConcreteSubject extends Subject{ private String subjectState; public void setSubjectState(String subjectState) { this.subjectState = subjectState; } }
3)抽象观察者类
/** * 抽象观察者 * @author Administrator */ public abstract class Observer { public abstract void update(); }
4)具体观察者类
/** * 具体观察者类 * @author Administrator */ public class ConcreteObserver extends Observer{ private String obserName; public ConcreteObserver(String obserName) { this.obserName = obserName; } @Override public void update() { System.out.println("状态发生改变,"+obserName +"更新!"); } }
5)客户端类
/** * 客户端类 * @author Administrator */ public class Client { public static void main(String[] args) { ConcreteSubject subject = new ConcreteSubject(); subject.attach(new ConcreteObserver("观察者1")); subject.attach(new ConcreteObserver("观察者2")); subject.setSubjectState("新状态"); subject.notifyObserver(); } }
5.2 效果
状态发生改变,观察者1更新! 状态发生改变,观察者2更新!
5.3 分析
在目标类中定义了观察者的集合,当有状态改变时,遍历通知这些观察者更新。