在项目设计阶段,处理一对多的依赖关系类的时候,我们需要降低代码的耦合性从而增强可扩展性,比如一个班级,班主任老师和学生的关系,对于学校的通知,必定不会是学生没事的时候就问一下班主任”学校有通知没啊?”(铁定会把班主任搞毛的),明智的做法则是等着班主任在班级里面通知(对于学校的通知,班主任不会不通知学生的),在这个关系里,班主任就是所谓的被观察者,而学生则是观察者,也就是所谓的观察者模式:
观察者模式:定义了对象之间的一对多的依赖,这样一来,当一个对象改变状态的时候,他的所有依赖都会收到通知并自动更新
对于观察者模式中所说的通知,就是在被观察者的状态改变的时候,能够让所有观察者根据这种变化作出反应,对于被观察者,他的手里应该有一张观察者的名单,只有这样,才能在状态改变的时候,给出观察者通知,就如上面的例子,班主任只有知道他们班有哪些学生,才能通知到位,当然有的时候,有的学生并不想知道学校的那些通知,那么他就要从老师那边把自己的名字从通知名单中删除掉,但是如果有一天他又想听了,那么对名单还有提供增加一个观察者的名单,之所以命名为观察者和被观察者,而不是通知者和被通知者,就是因为观察者有是否观察的主动权,按照前面一章所讲的,针对接口编程,我们就可以设计出一个被观察者的接口:
public interface Observerable{ public void addObserver(Observer o); public void deleteObserver(Observer o); public void notifyChanged(); }
对于观察者,他的职责就是等着被观察者的更新,然后更新自己的状态,我们也设计出他的接口
public interface Observer{ public void update(object[] data); }
很明显的观察者在运行的时候,必须知道知道自己的观察对象是谁,所以在观察者类中应该有个变量记录被观察者:
public class Observer1 implements Observer{ private Observerable subject; public Observer1(Observerable subject) { this.subject=subject; subject.addObserver(this); } public void update(object[] data) { ........ } }
在java的java.until包中 也提供了这两个接口,但是与我们不同的是,他的被观察者ObserverAble不是一个接口而是一个类,其中提供了setChanged()的这个函数,这个函数的作用就是设定changed的值从而决定是否通知所有的观察者是否更新,因为有些变化并不一定是要通知观察者,比如学校专门给老师发的工资调整的通知,这个真的有必要告诉学生么?(另外需要注意的是,java这个ObserverAble类,提供的setChanged方法是protected的,所以你要是用它,就必须继承这个类,如果你要同时继承另外一个类的话,….)
另一个问题,学生向学校提交了一份申请,但是,老师那边久久没有回应,怎么办,学生一直等下去么?肯定不行的,必定是要主动向老师询问结果的,这也就意味着,我们的观察者可以主动的从被观察者那边获取数据,那么观察者就必须提供对应数据的get方法。
另外这一章中也提到了一个新的设计原则:
为交互对象间的松耦合设计而努力