android开发中观察者模式的实际应用

来源:互联网 发布:淘宝买家怎么导出订单 编辑:程序博客网 时间:2024/06/04 11:13

我之前一直有听着观察者模式,但是一直没怎么实际运用过,后来在做项目的过程中,在一些前辈的指导下,学会了运用观察者模式到实际的项目当中,其实观察者模式对于我们项目的帮助还是蛮大的,自动通知各个观察者当前状态的变化,是一个十分有用的设计模式。

这次运用的在登陆过程中的观察者模式,当用户已经注册过应用,就直接进入,没有注册,就注册保存,并且当用于退出时,做相应的修改,当用户信息修改时,也要做相应得通知。实际上就是当用户的信息变更时,系统能够通知各个监听用户状态的观察者,从而做出相应的行为。

首先是观察者模式的基本方法:

1.创建一个观察者类,采用弱引用的方法,不容易导致内存泄露,不清楚弱引用的可以看看这篇 http://blog.csdn.net/matrix_xu/article/details/8424038:

public class DataObserver{    private WeakReference<Object> mReferenceObserver = null;    /**     *     */    public DataObserver(Object observer)    {        mReferenceObserver = new WeakReference<Object>(observer);    }    public Object getObserver()    {        if (mReferenceObserver != null)        {            return mReferenceObserver.get();        }        return null;    }}
2.创建一个观察者池,说白了就是用对观察者的增删查改,设置key值为观察者的唯一标识符。

public class DataObserverPool{//private static final String TAG = "LogicManagerObserverPool";    protected Map<String, List<DataObserver>> mObserverMap;    /**     *     */    public DataObserverPool()    {        mObserverMap = new HashMap<String, List<DataObserver>>();    }    /**     * 添加监听者     * @param key     * @param observer     */    public void addObserver(String key, DataObserver observer)    {        List<DataObserver> observerList = getObservers(key);        if (observerList == null)        {            observerList = new ArrayList<DataObserver>();            mObserverMap.put(key, observerList);        }        observerList.add(observer);    }    /**     * 根据key删除监听     * @param key     * @param observer     */    public void removeObserver(String key, DataObserver observer)    {        List<DataObserver> observerList = getObservers(key);        if (observerList != null)        {            observerList.remove(observer);        }    }    /**     * 获取所有监听者     * @param key     * @return     */    public List<DataObserver> getObservers(String key)    {        List<DataObserver> observerList = mObserverMap.get(key);        return observerList;    }    /**     * 删除该key的所有监听     * @param key     */    public void removeObservers(String key)    {        mObserverMap.remove(key);    }    /**     * 获取所有监听key     * @return     */    public Set<String> getAllKey()    {        return mObserverMap.keySet();    }    /**     * 删除该监听者的所有监听     * @param observer     */    public void removeObserver(DataObserver observer)    {        Set<String> keySet = mObserverMap.keySet();        Iterator<String> iterator = keySet.iterator();        while (iterator.hasNext())        {            String key = iterator.next();            List<DataObserver> observerList = mObserverMap.get(key);            observerList.remove(observer);        }    }}
3.穿件完成后,就可以在baselogicmanager当中写几个方法来添加:

/**     * @param key 要监听的key     * @param observer 要被通知的observer     */    protected void addObserver(String key, Object observer)    {        if (mObserverPool == null)        {            mObserverPool = new DataObserverPool();        }        DataObserver logicManagerObserver = new DataObserver(observer);        mObserverPool.addObserver(key, logicManagerObserver);    }    /**     *     * @param key 要移除监听的key     * @param observer 要被通知的observer     */    protected void removeObserver(String key, Object observer)    {        if (mObserverPool == null) return;        List<DataObserver> logicManagerObservers = mObserverPool.getObservers(key);        if (logicManagerObservers == null) return;        DataObserver removeLogicManagerObserver = null;        for (DataObserver logicManagerObserver : logicManagerObservers)        {            if (observer == logicManagerObserver.getObserver())            {                removeLogicManagerObserver = logicManagerObserver;                break;            }        }        if (removeLogicManagerObserver != null)        {            mObserverPool.removeObserver(key,                    removeLogicManagerObserver);        }    }    /**     *     * @param key     */    protected List<Object> getObservers(String key)    {        List<Object> observerObjectList = new ArrayList<Object>();        if (mObserverPool == null)            return observerObjectList;        List<DataObserver> observers = mObserverPool.getObservers(key);        if (observers != null)        {            for (DataObserver observer : observers)            {                Object observerObject = observer.getObserver();                if (observerObject != null)                {                    observerObjectList.add(observerObject);                }            }        }        return observerObjectList;    }    /**     *     * @param key     */    protected void removeObservers(String key)    {        if (mObserverPool == null)            return;        mObserverPool.removeObservers(key);    }    /**     *     * @param observer     */    protected void removeObserver(Object observer)    {        if (mObserverPool == null) return;        Set<String> keySet = mObserverPool.getAllKey();        Iterator<String> iterator = keySet.iterator();        while (iterator.hasNext())        {            String key = iterator.next();            removeObserver(key, observer);        }    }

4.然后就到了实际的应用了,首先是得在interface当中设置好引用的接口

    /**     * 添加对账户状态变化的观察     * @param observer     */    void addAccountStateObserver(IAccountStateObserver observer);    /**     * 删除对账户状态变化的观察     * @param observer     */    void removeAccountStateObserver(IAccountStateObserver observer);    interface IAccountStateObserver    {        void onAccountLogined();        void onAccountLogouted();    }
然后在accountmanager当中实现上面的两个方法:

@Override    public void addAccountStateObserver(IAccountStateObserver observer)    {        addObserver(OB_KEY_ACCOUNT_STATE, observer);    }    @Override    public void removeAccountStateObserver(IAccountStateObserver observer)    {        removeObserver(OB_KEY_ACCOUNT_STATE, observer);    }



5.例如我再addressManager当中要监听用户的状态是否发生了变化,就可以用这两个公共的方法来添加OB_KEY_ACCOUNT_STATE类的观察者:

public AddressManager()    {        LogicService.accountManager().addAccountStateObserver(this);    }
当然,AddressManager得首先实现IAccountStateObserver这个接口,然后就可以在两个接口当中对各自进行操作:

@Override    public void onAccountLogined()    {    }    @Override    public void onAccountLogouted()    {        mAddressList.clear();        mDefaultAddress = null;    }


6.最重要的事可别忘了,我们还没通知各个观察者,当然是在state发生变化时通知各个观察者:

例如我再请求用户信息,更新用户信息成功时,就可以通知管擦或者:

List<Object> observers = getObservers(OB_KEY_ACCOUNT_STATE);                if (observers != null)                {                    for (Object object : observers)                    {                        IAccountStateObserver observer = (IAccountStateObserver) object;                        observer.onAccountLogined();                    }                }

或者

 List<Object> observers = getObservers(OB_KEY_ACCOUNT_STATE);        if (observers != null)        {            for (Object object : observers)            {                IAccountStateObserver observer = (IAccountStateObserver) object;                observer.onAccountLogouted();            }        }
通过这样的设置,我们就可以通知各个观察者来进行各自的操作了,这样我们就能很方便的管理,不用每个类都去写各自的操作。

不足之处,望多多指教。







0 0