java定义了一种观察者接口对象,用于所有观察者类去实现它。也可以自定义的创建观察者接口,其中的原理都是差不多.
现在来简述第一种自定义观察者的原理:
1.首先建立一个观察者接口MyObserver.java,并写上抽象方法(当观察的目标改变了就会执行的更新操作),代码如下:
/** * *这是观察者的抽象类,其他实体的观察者都要去实现它; */ public interface MyObserver { /** * 更新 * @param subject */ public void update(MySubject subject); }
这里的update方法中传了 要观察的目标对象;
2.创建一个目标对象,作为所有观察者的目标对象,也是所有目标的父类;其中代码如下:
1 import java.util.ArrayList; 2 /** 3 * 观察者的目标类 4 * @author Administrator 5 * 6 */ 7 public class MySubject { 8 9 public ArrayList<MyObserver> mObservers = new ArrayList<MyObserver>(); 10 11 /** 12 *添加观察者到 列表里, 13 *代表了所有的观察该目标的观察者 14 * @param obs 15 */ 16 public void attach(MyObserver obs){ 17 mObservers.add(obs); 18 } 19 /** 20 * 移除 在观察目标该列表里的观察对象 21 * @param obs 22 */ 23 public void datach(MyObserver obs){ 24 mObservers.remove(obs); 25 } 26 27 /** 28 * 当目标值改变,就应该调用的方法 29 * 这个方法是去刷新观察者列表里的每个观察者对象,这样观察者对象就会做出改变 30 */ 31 public void notifyMyObserver(){ 32 for(int i=0;i<mObservers.size();i++){ 33 MyObserver observer = mObservers.get(i); 34 observer.update(this); 35 } 36 } 37 }
就这样,自定义观察者中的基类就写完 了;
有了这两个基类,我们就可以做点示例的东西来诠释一下观察者模式的用处:
1.假设 两个对象,一个是学生Student.java ,一个是天气Weather.java ,学生去观察天气的变化;
天气作为目标,继承了目标基类,代码如下:
1 public class Weather extends MySubject { 2 3 //天气的属性 4 private String info; 5 private String action; 6 7 public String getInfo() { 8 return info; 9 } 10 /** 11 * @param info 12 * @param action 13 * 当set 来改变目标时。观察者就会得到刷新 14 */ 15 public void setInfo(String info,String action) { 16 this.info = info; 17 this.action = action; 18 notifyMyObserver(); 19 } 20 public String getAction() { 21 return action; 22 } 23 24 25 26 }
解释一下,当天气的通过set方法来改变时,就会执行notifyMyobserver()方法,而观察者就会做出回应;
2,学生作为观察者来实现MyObserver接口,并实现该功能;代码如下:
1 /** 2 * 学生是观察者之一,而学生 观察的目标 是 天气 3 * 4 * @author Administrator 5 * 6 */ 7 public class Student implements MyObserver { 8 9 //增加学生的属性 10 private String name; 11 private String sex; 12 private int age; 13 14 public Student(String name,String sex){ 15 this.name = name; 16 this.sex = sex; 17 } 18 /* (non-Javadoc) 19 * @see MyObserver#update(MySubject) 20 * 实现方法 21 */ 22 @Override 23 public void update(MySubject subject) { 24 Weather weather = (Weather) subject;//将父类对象强制转换为 子类对象 25 26 //获取到监督的目标对象的信息 27 String info = weather.getInfo(); 28 String action = weather.getAction(); 29 //打印 30 if(info.equals("下雨")){ 31 System.out.println("今天是:"+info+" "+name+"将要去"+action); 32 } 33 34 } 35 36 }
这里的关系有些绕,多看看就可以理解到位;
到这里自定义的观察者模式就演示完了
那么现在来看看简单的java库中的 观察者模式;
同样的原理,但是这里就不用去定义接口观测者,和目标基类,而是使用java库的;
先贴出,Weather.java目标类代码如下:
1 import java.util.Observable; 4 public class Weather extends Observable{ 5 private String info; 6 private String wendu; 7 public String getInfo() { 8 return info; 9 } 10 public void setInfo(String info,String wendu) { 11 this.info = info; 12 this.wendu = wendu; 13 setChanged();//改变了目标 14 /* 15 * 这里有两个方法,分别notifyObservers(),notifyObservers(org)有参数和无参数;有参数的刷新方法,就会传递 16 对应的参数到 观察者的 update(Observable arg0, Object arg1)中的 org1,而无参的刷新方法中,传入的是整个目标对象arg0 17 */ 18 notifyObservers();//java中定义的,就是继承了 目标观察者的方法,去刷新观察者 19 //notifyObservers(wendu); 20 } 21 public String getWendu() { 22 return wendu; 23 } 26 }
那么,student.java观察者类代码:
1 import java.util.Observable; 2 import java.util.Observer; 3 4 5 /** 6 * @author Administrator 7 * 实现java中定义好的 观察者接口,其实现方法和自定义的类似 8 * 9 */ 10 public class Student implements Observer { 11 //增加学生的属性 12 private String name; 13 private String sex; 14 private int age; 15 16 public Student(String name,String sex){ 17 this.name = name; 18 this.sex = sex; 19 } 20 21 /* (non-Javadoc) 22 * @see java.util.Observer#update(java.util.Observable, java.lang.Object) 23 这里的 24 */ 25 @Override 26 public void update(Observable arg0, Object arg1) { 27 Weather w = (Weather) arg0; 28 //获取到监督的目标对象的信息 29 String info = w.getInfo(); 30 String action = w.getWendu(); 31 //打印 32 if(info.equals("下雨")){ 33 System.out.println("今天是:"+info+" "+name+"将要去"+action); 34 } 35 36 } 37 38 39 40 41 }
在来个测试类代码,
1 /** 2 * @author Administrator 3 *这是个测试类 4 */ 5 public class main { 6 public static void main(String args[]) { 7 8 //写观察者的目标对象 9 Weather w = new Weather(); 10 11 //两个学生的观察者 12 Student st1 = new Student("小剑", "38"); 13 Student st2 = new Student("gooddog", "39"); 14 15 //用java中定义好的添加方法来吧目标 添加观察者对象(就是让这些观察者去观察它) 16 w.addObserver(st2); 17 w.addObserver(st1); 18 19 //通过set来怪不数据,测试观察者数据是否会随着改变 20 w.setInfo("下雨", "去网吧"); 21 } 22 }
嗯,到这里观察这模式就结束了,通过控制台打印就可以看到,改变了weather set方法的,就可打印出不同的值;
具体的就个人去测试吧;如果要源码就请留言。
”原创,转载请标注“