1、抽象观察者介绍
观察者模式定义了一种对象间的一对多的依赖关系,即每当一个对象状态改变时,所依赖于他的所有对象都要被通知并自动更新。观察者模式的组成部分包括:
1)抽象观察者角色:为那些在目标发生改变时需要获得通知的对象提供一个接口
2)具体观察者角色:存储有关状态,这些状态应该与目标状态保持一致
3)抽象目标角色:目标角色知道它的观察者,可以有任意多个观察者观察同一个目标,并且提供了添加、删除观察者对象的接口
4)具体目标角色:当状态发生改变时,向它的所有观察者发送通知
其中抽象观察者角色和抽象目标角色是 jdk 中的 Observer.java 和 Observable.java 所定义。
从上图可以看出,observer.java提供了一个update方法,只要改变了 observable 对象就调用此方法。observable.java提供了添加观察者,删除清空观察者,以及标记此
observable对象已改变的方法。
下面通过一个代码示例来进一步说明:
1)定义了两个观察者(邮件观察者和短信观察者)
package demo.design.observer;
import java.util.Observable;
import java.util.Observer;
public class SMSSendObserver implements Observer{
//通过构造器的方式给Product注入短消息发送观察者
public SMSSendObserver(Product product) {
product.addObserver(this);
}
public void update(Observable product, Object arg) {
System.out.println("Product price has been changed to "
+ ((Product)product).getPrice()
+ " ;\n\t\t The notify SMS has sent to all client.");
}
}
package demo.design.observer;
import java.util.Observable;
import java.util.Observer;
public class EmailSendObserver implements Observer{
//通过构造器的方式给Product注入邮件发送观察者
public EmailSendObserver(Product product) {
product.addObserver(this);
}
public void update(Observable product, Object arg) {
System.out.println("Product price has been changed to "
+ ((Product)product).getPrice()
+ " ;\n\t\t The notify e-mail has sent to all client.");
}
}
2)定义一个具体目标角色(一个产品)
package demo.design.observer;
import java.util.Observable;
public class Product extends Observable {
//构造器
private Product(){
}
//构造器
public Product(float price){
this.price = price;
}
//商品价格
private float price;
//改变商品价格
public void changePrice(float price) {
if (this.price != price) {
this.price = price;
setChanged();
}
notifyObservers();
}
public float getPrice() {
return price;
}
public void setPrice(float price) {
this.price = price;
}
}
3)测试
package demo.design.observer;
public class ObserverTest {
public static void main(String[] args) {
//new product
Product product = new Product(2000);
//email observer
new EmailSendObserver(product);
//sms observer
new SMSSendObserver(product);
//chage price of product
product.changePrice(1400);
}
}
从上面例子可以看出,我们继承Observer这个抽象观察者接口,定义了两个具体观察者:邮件观察者和短信观察者。然后定义了一个Product 产品并继承Observable类,
并在具体产品类的changePrice 改变产品价格方法中,调用父类(observable类)的setChanged方法来标记该observable对象已经被改变,然后调用父类的notifyObservers方
法,通知它的所有观察者。这样在价格改变的时候,观察者就会向需要通知的对象发送消息。
2、抽象观察者优点
对象之间可以进行同步通信
可以通知多个关联对象
对象之间是松耦合的,不相互依赖,修改彼此不会造成影响,易于维护。