设计模式之观察者模式实践
2016-01-26 18:25
441 查看
观察者模式的角色组成
1:抽象主题(Subject)角色:主题角色把所有的观察者对象的引用保存在一个列表里;每个主题都可以有任何数量的观察者。主题提供一个接口可以加上或撤销观察者对象;主题角色又叫做抽象被观察者(Observable)角色;
抽象主题角色,有时又叫做抽象被观察者角色,可以用一个抽象类或者一个接口实现;在具体的情况下也不排除使用具体类实现。
2:抽象观察者(Observer)角色:
为所有的具体观察者定义一个接口,在得到通知时更新自己;
抽象观察者角色,可以用一个抽象类或者一个接口实现;在具体的情况下也不排除使用具体类实现。
3:具体主题(ConcreteSubject)角色:
保存对具体观察者对象有用的内部状态;在这种内部状态改变时给其观察者发出一个通知;具体主题角色又叫作具体被观察者角色;
具体主题角色,通常用一个具体子类实现。
4:具体观察者(ConcreteObserver)角色:
保存一个指向具体主题对象的引用;和一个与主题的状态相符的状态。具体观察者角色实现抽象观察者角色所要求的更新自己的接口,以便使本身的状态与主题的状态自恰。
具体观察者角色,通常用一个具体子类实现。
程序实践
1:Observerpublic interface Observer { public void update(String str); }
2:ConcreteObserver1
public class ConcreteObserver1 implements Observer{ @Override public void update(String str) { System.out.println("手机客户端--->"+str); } }
3:ConcreteObserver2
public class ConcreteObserver2 implements Observer{ @Override public void update(String str) { System.out.println("PC"+ "客户端--->"+str); } }
4:Subject
public interface Subject { public void addWatcher(Observer watcher); public void removeWatcher(Observer watcher); public void notifyWatchers(String str); }
5:ConcreteSubject
import java.util.ArrayList; import java.util.List; public class ConcreteSubject implements Subject{ // 存放观察者 private List<Observer> list = new ArrayList<Observer>(); @Override public void addWatcher(Observer watcher) { list.add(watcher); } @Override public void removeWatcher(Observer watcher) { list.remove(watcher); } @Override public void notifyWatchers(String str) { // 自动调用实际上是主题进行调用的 for (Observer watcher : list) { watcher.update(str); } } }
6:Test
import java.io.IOException; import java.util.Map; public class Test { public static void main(String[] args) throws NullPointerException, IOException { Subject subject = new ConcreteSubject(); Observer observer1 = new ConcreteObserver1(); Observer observer2 = new ConcreteObserver2(); subject.addWatcher(observer1); subject.addWatcher(observer2); Map<String, Object> map = WeatherUtil.getTodayWeather("101010100"); subject.notifyWatchers(map.get("city") + ":" + map.get("temp")+ "度(发布时间:" + map.get("time")+")"); } }
运行结果
手机客户端--->北京:10度(发布时间:10:25) PC客户端--->北京:10度(发布时间:10:25)
观察者模式的应用场景
1、 对一个对象状态的更新,需要其他对象同步更新,而且其他对象的数量动态可变。2、 对象仅需要将自己的更新通知给其他对象而不需要知道其他对象的细节。
观察者模式的优点:
1、 Subject和Observer之间是松偶合的,分别可以各自独立改变。2、 Subject在发送广播通知的时候,无须指定具体的Observer,Observer可以自己决定是否要订阅Subject的通知。
3、 遵守大部分GRASP原则和常用设计原则,高内聚、低偶合。
观察者模式的缺陷
1、 松偶合导致代码关系不明显,有时可能难以理解。2、 如果一个Subject被大量Observer订阅的话,在广播通知的时候可能会有效率问题。(毕竟只是简单的遍历)
相关文章推荐
- Android Native 绘图方法
- Python动态类型的学习---引用的理解
- PropertyChangeListener简单理解
- 什么是设计模式
- 设计模式之创建型模式 - 特别的变量问题
- 七、设计模式——装饰模式
- 设计模式总结
- 设计模式之创建型模式
- 浅谈设计模式的学习
- 土人系列AS入门教程 -- 对象篇
- C#托管堆对象实例包含内容分析
- C#中struct和class的区别详解
- C#实现获取不同对象中名称相同属性的方法
- javascript asp教程第十一课--Application 对象
- PowerShell中使用Out-String命令把对象转换成字符串输出的例子
- VBS ArrayList Class vbs中的数组类
- VBS教程:对象-正则表达式(RegExp)对象
- 大家看了就明白了css样式中类class与标识id选择符的区别小结
- C#检查指定对象是否存在于ArrayList集合中的方法
- sql2008启动代理未将对象应用到实例解决方案