Android之观察者/被观察者模式Observer/Observable
来源:互联网 发布:淘宝企业店铺搜索 编辑:程序博客网 时间:2024/05/20 12:48
Android之观察者Observer初探
文章链接:http://blog.csdn.net/qq_16628781/article/details/62446146
知识点:
1、Android观察者模式的简介;
2、Observer和Observable的使用实例;
3、(abstract)抽象类和抽象方法的使用;
4、新名词记录
{
abstract:抽象关键词
}
最近一直在看着观察者模式的rxjava/rxandroid,但是我却忽略了在Java中,也是有这个观察者的。这也是我在一个项目中偶然看到的一个名词,然后我就去搜索着来看了,不看不知道,一看吓一跳,原来这里头有这么深的水啊。只怪自己阅历不够了。
观察者模式:简单来说,就是当对象A对对象B进行进行了类似“订阅”关系,当对象B的数据发生改变时,就要通知对象A进行相应。很简单也很好理解。Android中的观察者需要实现Observer接口,当数据发生改变时,观察者的update()方法就会被调用,被观察者继承Observable类,在数据发生改变时,需要调用setChanged(); this.notifyObservers(obj);这两个方法才可以通知观察者:你想要知道的数据发生了变化了。
在学习这个观察者模式的时候,脑袋突然开窍了,顺便加固了一把抽象类/抽象方法的使用,之前看了N多的关于abstract关键字的学习,但是苦于一直没有能够真正的理解abstract关键的实际使用用途,只停留在了知识层面,木有应用。
今天弄这个观察者模式的时候,想着我要把数据如何在单元测试中打印出来的问题时,我写了一个abstract抽象方法,然后然后然后我就懂了这个要怎么用了。实在可喜可贺啊!!!
好了,废话不多说了,下面直接上代码,我都在代码里头做了注释了,各位看官请直接看下面的代码。
首先定义一个继承Observable的被观察者LoginOutObservable.java抽象类。
package com.yaojt.sdk.java.observer;import java.util.Observable;/** * desc:被观察者类,被观察者如果数据发生变化,则需要通知观察者,数据发生了改变,需要做相应的操作 * <p> * author:kuyu.yaojt (tanksu) * <p> * email:yaojt@kuyumall.com * <p> * blog:http://blog.csdn.net/qq_16628781 * <p> * date:17/3/16 */public abstract class LoginOutObservable extends Observable { private String userName = "admin"; /** * 设置是否登出,如果是,则需要通知观察者 * * @param isLoginOut isLoginOut */ public void setLoginOut(boolean isLoginOut) { if (isLoginOut) { String data = "被观察者告诉你:你已经退出登录,请重新登录!"; /* 注意注意注意:下面这两个方法是要同时调用的,否则不会通知观察者数据发生了变化 */ setChanged(); this.notifyObservers(data); onUserLoginOut("这是在被观察者内部调用的方法:" + data); } } /** * 设置用户名,如果用户名和上次的不一样,则需要通知观察者 * * @param name name */ public void setUserName(String name) { if (!name.equals(userName)) { this.userName = name; String data = "被观察者告诉你:用户名已经改变了!新的名字为:" + name; /* 注意注意注意:下面这两个方法是要同时调用的,否则不会通知观察者数据发生了变化 */ setChanged(); this.notifyObservers(data); onUserNameChanged("这是在被观察者内部调用的方法:" + data); } } /** * 当用户名字发生改变时,用于在本类中将数据打印出来 * <p> * 感悟: * 抽象方法,凡是继承此类的子类,都需要重写此方法 * 但是我们可以再本类里调用此方法,然后实例化此类的时候,要求实现类实现本类里头的抽象方法 * * @param newUserName */ public abstract void onUserNameChanged(String newUserName); /** * 当用户登出时,在本类中用于将数据打印出来 * <p> * 感悟: * 抽象方法,凡是继承此类的子类,都需要重写此方法 * 但是我们可以再本类里调用此方法,然后实例化此类的时候,要求实现类实现本类里头的抽象方法 * * @param message message */ public abstract void onUserLoginOut(String message);}
然后再定义一个继承Observer的观察者LoginoutObserver.java。
package com.yaojt.sdk.java.observer;import java.util.Observable;import java.util.Observer;/** * desc: * <p> * author:kuyu.yaojt (tanksu) * <p> * email:yaojt@kuyumall.com * <p> * blog:http://blog.csdn.net/qq_16628781 * <p> * date:17/3/16 */public abstract class LoginoutObserver implements Observer { @Override public void update(Observable o, Object arg) { /* 当被观察者因为数据发生了改变,并通知了相关的观察者后,观察者将会调用此方法进行相应 * 我们这里调用的是本地的抽象方法进行数据输出 */ onDataChanged("观察者从被观察者中的消息:", arg); } /** * 这里给出一个抽象方法给实现类实现,然后我们会在updat()方法被调用的时候,调用这个方法,给实现类相应 * * @param message message * @param object object */ public abstract void onDataChanged(String message, Object object);}最后我们就可以在单元测试里头进行测试了,如果又不熟悉IDE上面如何进行单元测试的,请看这篇文章点击打开链接,我就不细讲了。
@Test public void observerTest() { /* 被观察者:登出/修改用户名类,实例 */ LoginOutObservable loginOutObservable = new LoginOutObservable() { @Override public void onUserNameChanged(String newUserName) { printer(newUserName); } @Override public void onUserLoginOut(String message) { printer(message); } }; /*观察者1:并实现了观察者类的抽象方法,实现在这里进行数据的打印输出 */ LoginoutObserver loginoutObserver1 = new LoginoutObserver() { @Override public void onDataChanged(String message, Object object) { printer("我是观察者1-->" + message + "," + object.toString()); } }; /*观察者2:并实现了观察者类的抽象方法,实现在这里进行数据的打印输出 */ LoginoutObserver loginoutObserver2 = new LoginoutObserver() { @Override public void onDataChanged(String message, Object object) { printer("我是观察者2-->message:" + message + "," + object.toString()); } }; LoginoutObserver loginoutObserver3 = new LoginoutObserver() { @Override public void onDataChanged(String message, Object object) { printer("我是观察者3-->message:" + message + "," + object.toString()); } }; /** * 这里像是被观察者订阅了观察者,看起来是有点别扭的哈; * 就像和反射里面调用invoke方法:method.invoke(obj, args); * 具体可以参考这篇文章: * 但是不要被混淆了,最好记的一点就是:外国人说话看起来都是和中文"反过来"的 */ loginOutObservable.addObserver(loginoutObserver1); loginOutObservable.addObserver(loginoutObserver3); loginOutObservable.addObserver(loginoutObserver2); /* 这里是模拟被观察者登出操作,登出了必须要通知用户重新登录啊 */ loginOutObservable.setLoginOut(true); /* 这里是模拟被观察者修改了用户名操作,导致前后用户名不一致而引起数据变化了 */ loginOutObservable.setUserName("tanksu"); }public void printer(String content) { System.out.println(content); }
运行的结果如下:
如果你够细心的话,你会发现一个问题:我们观察者new的时候,是按着1->2->3的顺序来的,但是怎么数据改变时,调用的观察者方法却是反过来的呢,变成了2->3->1。猛地一看,发现这是我进行“订阅”被观察者的倒序呢。这里我们可以得到一个结论:在数据发生改变时,被观察者通知观察者的循序是遵循“先订阅后通知”的循序。这里要注意一下。
以上就是我的个人简介。
如果有任何疑问,请及时与我联系。谢谢。
- Android之观察者/被观察者模式Observer/Observable
- android Observable and Observer(观察者模式)
- android Observable and Observer(观察者模式)
- 观察者模式(Observer、Observable)
- Observable与Observer (观察者模式)
- Java观察者模式 : Observer / Observable
- java 观察者模式Observable Observer
- 设计模式之观察者模式(Observable与Observer)
- 设计模式之观察者模式(Observable与Observer)
- 设计模式之观察者模式(Observable与Observer)
- Java基础之Observable与Observer接口观察者模式
- Java_观察者模式(Observable和Observer)
- java observer和observable 实现观察者模式
- 十一、观察者模式(Observable、Observer)
- 观察者模式-java 内置 Observable 和 Observer
- 利用Observable、Observer实现观察者模式
- Java_观察者模式(Observable和Observer)
- 浅谈 Observable和Observer 观察者模式
- tomcat启动服务后浏览器无法显示网页
- js常识
- hibernate 与 mybits 的区别
- Dagger2学习之路(Part 1)
- 病毒
- Android之观察者/被观察者模式Observer/Observable
- CSS布局(绝对定位/相对定位/浮动/显示与隐藏/居中)(好)
- 设计模式----行为型模式之观察者模式(Observer Pattern)
- react native 带索引的城市列表
- 二叉树、哈希表
- 杭电1005.找规律就好
- Git理解及常用操作总结
- Java基本类型和引用类型(参数传递)
- word中插入高分辨率图片,并且保存为PDF图片仍然高清的方法