定义
观察者模式(Observer Pattern)定义对象间的一种一对多的依赖关系,当一个对象的状态发生改变时,所有依赖于它的对象都得到通知并被自动更新。
别名
依赖(dependent)、发布-订阅(publish-subscribe)
结构图
参与者
· Subject(目标):目标知道它的观察者。可以有任意多个观察者观察同一个目标。提供注册和删除观察者对象的接口。
· Observer(观察者) :为那些在目标发生改变时需要获得通知的对象定义一个更新接口。
· ConcreteSubject(具体目标) : 将有关状态存入各ConcreteObserver对象。当它的状态发生改变时,向其各个观察者发出通知。
· ConcreteObserver(具体观察者): 维护了一个指向ConcreteSubject的引用。储存有关状态,这些状态应与目标的状态保持一致。实现Observer的更新接口,以使自身状态与目标的状态保持一致。
优点
1、观察者和被观察者是抽象耦合的。
2、支持广播通信。
缺点
1、如果一个被观察者对象有很多的直接和间接的观察者的话,将所有的观察者都通知到会花费很多时间。
2、如果在观察者和观察目标之间有循环依赖的话,观察目标会触发它们之间进行循环调用,可能导致系统崩溃。
3、观察者模式没有相应的机制让观察者知道所观察的目标对象是怎么发生变化的,而仅仅只是知道观察目标发生了变化。
观察者模式的实现
1、 抽象目标类典型代码
import java.util.List;
import java.util.ArrayList;
public abstract class Subject {
//定义一个观察者集合用于存储所有观察者对象
protected List<Observer> observers = new ArrayList();
//注册方法,用于向观察者集合中增加一个观察者
public void attach(Observer observer) {
observers.add(observer);
}
//注销方法,用于在观察者集合中删除一个观察者
public void detach(Observer observer) {
observers.remove(observer);
}
//声明抽象通知方法
public abstract void notify();
}
具体目标类
public class ConcreteSubject extends Subject {
//实现通知方法
public void notify() {
//遍历观察者集合,调用每一个观察者的响应方法
for(Observer obs:observers) {
obs.update();
}
}
}
抽象观察者
public interface Observer {
//声明响应方法
public void update();
}
具体观察者
public class ConcreteObserver implements Observer {
//实现响应方法
public void update() {
//具体响应代码
}
}