关闭

Android观察者设计模式

标签: 设计模式ObservableObserver
91人阅读 评论(0) 收藏 举报
分类:

本文主要是为了学习RxJava,Retrofit这两个比较火的框架做铺垫的!


观察者两种的实现方式

  • 自定义模式
    其实这种自定义方式,也是模仿util包下Observable、Observer的实现方式,但本文还是讲解一下,更深刻理解以下。

  • 通过重写util包下的Observable(被观察者),Observer(观察者)


图形介绍

  • 被观察者

    这里写图片描述

  • 观察者

    这里写图片描述


自定义观察者模式

  • 声明:想这种自定义观察者模式,没有什么固定的写法,看大家的自己的思维模式怎么去设计了。所以不用纠结怎么写是对的。

  • 首先,我们需要创建一个观察者的接口和被观察者的接口(或抽象类)

    1.观察者的接口:对外提供一个方法,被观察者数据发生改变时调用此方法,同步最新数据

/**
 * Created by sswl on 2017/7/13.
 * 观察者接口
 */

public interface OnserverInterface {

    void update(String s);
}

2.被观察者接口(或抽象类):提供三个方法,如上图所示

/**
 * Created by sswl on 2017/7/13.
 * @see Subject  被观察者
 */

public abstract class Subject {

    /**
     * 管理所有观察者的集合
     * */
    private ArrayList<OnserverInterface> mList =new ArrayList<>();

    /**
     * @param onserver 增加某个观察者
     * */
    public void addObserver(OnserverInterface onserver){
        mList.add(onserver);

    }
    /**删除
     * @param  onserver 移除某个观察者
     * */
    public void deleteObserver(OnserverInterface onserver){
        mList.remove(onserver);

    }

    /**
     * @param state 通知所用的观察者
     * */
    public void notify(String state){

        for (OnserverInterface o : mList) {
            o.update(state);

        }
    }
}
  • 写两个帮助类,SubjectHelp(被观察者帮助类)和OnserverHelp(观察者帮助类)

    SubjectHelp(被观察者帮助类):

public class SubjectHelp extends Subject {

    /**
     * 当被观察者需要改变数据时,可以调用change   ,
     * change调用notify通知观察者数据改变
     * */
    public void  change(String s){
        notify(s);
    }
}

OnserverHelp(观察者帮助类):

public class OnserverHelp implements OnserverInterface {

    public String name;
    public OnserverHelp(String name){
        this.name=name;
    }

    @Override
    public void update(String s) {
        //这里的s 是数据发生改变时 在change(String s)方法里调用 notify(s);而 notify(s)里用调用了update(state);,这个s就是改变的数据,一直传递过来的。
        //如果用户想要显示在界面上,可以提供一个接口,把数据传到接口里,然后Activity实现这个接口就可以从接口里获取数据了(方式之一)
        Log.e("OnserverHelp","被观察者发生数据的改变,通知观察者: "+name+"》》》"+s);
    }
}
  • 下面进行实际操作,模拟场景:用户点击一个按钮然后数据发生改变(这里为了方便只是打印的log)
  /**
     * 自定义观察者模式
     * */
    private void initdata() {
        /**
         * 多个观察者
         * */
        onserverHelp = new OnserverHelp("詹姆斯.卡梅隆");
        OnserverHelp onserverHelp1 = new OnserverHelp("莱昂纳多");
        OnserverHelp  onserverHelp2 = new OnserverHelp("阿伦.艾弗森");
        /**
         * 被观察着   (可以一对多)
         * */
        subjectHelp = new SubjectHelp();
        /**
         * 给subjectHelp 添加观察者(可以添加多个观察者)
         * */
        subjectHelp.addObserver(onserverHelp);
        subjectHelp.addObserver(onserverHelp1);
        subjectHelp.addObserver(onserverHelp2);
        /**
         * 删除某个观察者  退出界面时也可以放到onDestroy里销毁
         * */
        subjectHelp.deleteObserver(onserverHelp2);

    }

然后用户点击按钮:

 btn.setOnClickListener(new View.OnClickListener() {
            @Override
            public void onClick(View v) {
            //被观察者数据发生改变
                subjectHelp.change("我是被观察者Observer");
                /**Log
                 * 07-13 10:00:46.236 25525-25525/webred.cp.example.com.observerapp E/OnserverHelp: 被观察者发生数据的改变,通知观察者: 詹姆斯.卡梅隆》》》我是被观察者Observer
                 * 07-13 10:00:46.236 25525-25525/webred.cp.example.com.observerapp E/OnserverHelp: 被观察者发生数据的改变,通知观察者: 莱昂纳多》》》我是被观察者Observer
                 * */
            }
        });

这样就实现了观察者设计模式,整个流程,initdata的时候给被观察者添加了两个观察者,用户点击按钮,调用了change(String s),s就是发生改变的数据,在change方法里用调用了notify(通知观察者数据发生改变),notify里又把s传递到了update(这个方法是观察者得到最新数据的方法)


java.util包下的观察者模式

import java.util.Observable;
import java.util.Observer;
 /**
     * android 自带的观察者模式的相关类
     * Observable 抽象类
     * Observer 接口
     * */
    private void androidObserverable() {
        androidHelpObserverable = new AndroidHelpObserverable("android自带的观察者模式类");
        androidObserverHelp = new AndroidObserverHelp("麦迪TMC");
        androidHelpObserverable.addObserver(androidObserverHelp);
    }
  • 同自定义一样,我们需要写一个被观察者帮助类和观察者帮助类
    被观察者帮助类:
public class AndroidHelpObserverable extends Observable {

    public String name;
    public AndroidHelpObserverable(String s) {
        this.name=s;
    }
    /***
     * 该方法
     * */
    public void  change(){
        setChanged();//数据发生改变时,该方法返回的是true(必须调用的)
        notifyObservers();
        // notifyObservers(“也可以调用有参数的,用户可以自己传递一些数据,同自定义观察者模式的传递数据一样”);
    }

}

观察者帮助类:

/**
 * Created by sswl on 2017/7/13.
 */

public class AndroidObserverHelp implements Observer {


    public String name;
    public AndroidObserverHelp(String name){
        this.name=name;
    }

    @Override
    public void update(Observable o, Object arg) {
        AndroidHelpObserverable observerable = (AndroidHelpObserverable) o;
        Log.e("android 自带的观察者模式相关类","观察者:"+name+"..."+observerable.name);
    }
}
  • 用户点击按钮
  btn1.setOnClickListener(new View.OnClickListener() {
            @Override
            public void onClick(View v) {
                androidHelpObserverable.change();
                /**log
                 * 07-13 10:18:42.645 30232-30232/webred.cp.example.com.observerapp E/android 自带的观察者模式相关类: 观察者:麦迪TMC...android自带的观察者模式类
                 * */
            }
        });
  • 退出界面时可以移除观察者
  @Override
    protected void onDestroy() {
        super.onDestroy();
        androidHelpObserverable.deleteObserver(androidObserverHelp);
        Log.e("退出界面时销毁:","销毁观察者");
    }

这就是观察者设计模式的两种实现方式!欢迎吐槽!


demo源码

0
0

查看评论
* 以上用户言论只代表其个人观点,不代表CSDN网站的观点或立场
    个人资料
    • 访问:19723次
    • 积分:679
    • 等级:
    • 排名:千里之外
    • 原创:48篇
    • 转载:3篇
    • 译文:0篇
    • 评论:7条