Observer模式

java语言里包含了许多对设计模式的直接支持,如command模式,agent模式,observer模式等。虽然java提供的对这些模式的支持很简单,不能满足比较复杂的应用。但在简单的场景下,使用这些类往往能够得到立杆见影的效果。所以,如果没有什么特殊需求,还是最好利用java的这些类。<?xml:namespace prefix = o ns = "urn:schemas-microsoft-com:office:office" />

Observer模式,又称监听模式,观察者模式,是经典设计模式之一(one of GOF)。java语言中,对这种模式支持的类和接口主要有以下几个,全部来自java.beans包:

java.beans.PropertyChangeListener (interface)

java.beans.PropertyChangeSupport(class)

java.beans.PropertyChangeEvent(class)

  • java.beans.PropertyChangeListener

这是一个接口,很显然,所有实现这个接口的类就是listener啦(或者叫observer),它会对被监听的对象的某些变化感兴趣。这个接口就一个方法:

java 代码

  1. publicvoidpropertyChange(PropertyChangeEventevt){

  2. //TODOAuto-generatedmethodstub

  3. }

接口定义很简单,作用也很明显。接受一个event(被监听者产生的PropertyChangeEvent),然后根据这个event做点反应。

  • java.beans.PropertyChangeSupport

这个类用在被观察者的类里,用来保存注册的观察者,并负责向他们提供被观察者的变化信息。这个类的方法也不多,不过还是只介绍100%用到的,要不脑子就不够使了,呵呵。

java 代码

  1. publicPropertyChangeSupport(ObjectsourceBean)

这是构造函数,参数就是被监听者。PropertyChangeListener一般作为被监听者的一个属性。一般如下使用:

java 代码

  1. privatePropertyChangeSupportlisteners=newPropertyChangeSupport(this);

注意,这个listeners可不是只代表一个监听者,他可能是一群监听者。那么如何这些listeners是谁呢?这回用到下面的方法了。

java 代码

  1. publicvoidaddPropertyChangeListener(PropertyChangeListenerlistener)

这个类太容易了,把监听者加进来。就像开十七大一样,记者想要采访,就得先登记一下。显然这个方法可以多次调用(add嘛)。有加就有减:

java 代码

  1. publicvoidremovePropertyChangeListener(PropertyChangeListenerlistener)

如果这个监听者对被监听者的任何变化多不感兴趣了,就被被监听者赶了出去。

好了,记者都到齐了,被监听者有变化了就该通知人家了,使用如下方法的一个:

java 代码

  1. publicvoidfirePropertyChange(PropertyChangeEventevt)

  2. publicvoidfirePropertyChange(StringpropertyName,

  3. booleanoldValue,

  4. booleannewValue)

  5. publicvoidfirePropertyChange(StringpropertyName,

  6. intoldValue,

  7. intnewValue)

  8. publicvoidfirePropertyChange(StringpropertyName,

  9. ObjectoldValue,

  10. ObjectnewValue)

实际上,后三个方法的参数都会封装成PropertyChangeEvent,然后调用第一个方法。不过在实际中,我们还是喜欢直接调用后三个中的一个,封装的事我们就不管了。后三个方法的参数都是三个,其中的oldValuenewValue就是改变前后的值,第一个就是给改变一个名字,好让监听者们根据这个名子来做响应。就像开会,政府的所有信息都会被记者听到,但是有的记者只对台湾问题感兴趣,而有的记者对中日问题感兴趣。

PropertyChangeSupport方法的介绍就这么多吧。注意,PropertyChangeSupport既然被用到了被观察者的类(一般是一个model)里,那么他的这些方法就只在被观察这里调用。

  • java.beans.PropertyChangeEvent

这个类我也懒得介绍,看看他的主要方法就明白怎么回事了

java 代码

  1. publicStringgetPropertyName()

  2. publicObjectgetNewValue()

  3. publicObjectgetOldValue()

就者三个类,再有就是具体问题具体分析了。来个例子吧,首先是被观察者:

java 代码

  1. publicclassDomain{

  2. protectedStringid;

  3. protectedStringname;

  4. protectedStringdesName;

  5. protectedPropertyChangeSupportlisteners=newPropertyChangeSupport(this);

  6. publicStringgetId(){

  7. returnid;

  8. }

  9. publicvoidsetId(Stringid){

  10. this.id=id;

  11. firePropertyChange("Domain.id",null,id);

  12. }

  13. publicStringgetDesName(){

  14. returndesName;

  15. }

  16. publicvoidsetDesName(StringdesName){

  17. this.desName=desName;

  18. firePropertyChange("Domain.desName",null,desName);

  19. }

  20. publicStringgetName(){

  21. returnname;

  22. }

  23. publicvoidsetName(Stringname){

  24. this.name=name;

  25. firePropertyChange("Domain.name",null,name);

  26. }

  27. publicvoidaddPropertyChangeListener(PropertyChangeListenerlistener){

  28. listeners.addPropertyChangeListener(listener);

  29. }

  30. publicvoidfirePropertyChange(StringpropName,ObjectoldValue,ObjectnewValue){

  31. listeners.firePropertyChange(propName,oldValue,newValue);

  32. }

  33. publicvoidremovePropertyChangeListener(PropertyChangeListenerlistener){

  34. listeners.removePropertyChangeListener(listener);

  35. }

  36. }

有人对Domain的三个属性感兴趣。下面就是这些人中的一个:

java 代码

  1. publicclassSimpleObserverimplementsPropertyChangeListener{

  2. ....

  3. @Override

  4. publicvoidpropertyChange(PropertyChangeEventevt){

  5. if(evt.getPropertyName().equals("Domain.name")){

  6. //dosomework

  7. }

  8. }

  9. }

下面是个简单的测试类:

java 代码

  1. publicclassSimpleTest{

  2. publicstaticvoidmain(String[]args){

  3. SimpleObserverobserver=newSimpleObserver();

  4. Domaindomain=newDomain();

  5. domain.addPropertyChangeListener(observer);

  6. domain.setName("yangsq");

  7. ......

  8. }

  9. }

很显然,可以观察到SimpleObserverpropertyChange方法的执行。

你可能感兴趣的:(java,设计模式,Microsoft,Office)