日更(十七)-Android-EventBus到底是個啥

瞎扯

干android有段時間的人,應(yīng)該都用過eventbus,rxbus之類的

那么,這個東西是怎么實現(xiàn)通信的.

其實要說原理的話,很簡單....

生產(chǎn)者/消費(fèi)者模式

說到生產(chǎn)者,消費(fèi)者.
可以想到handler.looper.也是生產(chǎn)者/消費(fèi)者,
這個是同步的.所以looper是個阻塞的死循環(huán)
就好比你去飯店排隊點(diǎn)餐.需要排隊
你排隊點(diǎn)餐就是生產(chǎn)者
點(diǎn)餐員就是消費(fèi)者

eventbus也是生產(chǎn)者/消費(fèi)者.
但是eventbus不需要同步.
這個是異步的,因為每個事件都有單獨(dú)的消費(fèi)者.

post =>register

register的回調(diào)是消費(fèi)者
post的event消息就是生產(chǎn)者.

實現(xiàn)bus的幾個點(diǎn)

一個單例

我們需要一個單例,里面有一個Map集合,來保存type.回調(diào),
但是一個type,可能有多種狀態(tài),所以再嵌套一層code.當(dāng)然只要你愿意,還可以在嵌套
不過我覺得2層已經(jīng)足夠了,

public class Event {
    //保存注冊的事件
    private static final Map<Class, Map<Object, Callback>> map = new HashMap<>();
}

register

就是把Type,和回調(diào),保存到集合里

 //注冊事件,消費(fèi)者
    public static void register(Class type, Object code, Callback callback) {
        Map<Object, Callback> callbackMap = map.get(type);
        if (callbackMap == null) {//判斷這個type,有沒有被注冊過
            callbackMap = new HashMap<>();
            callbackMap.put(code, callback);//添加code,與回調(diào)
            map.put(type, callbackMap);
        } else {
            callbackMap.put(code, callback);
        }
    }

Post方法

post方法,實際上實現(xiàn)就是,
去單例的集合里面,找出對應(yīng)的type.
然后取出回調(diào).把post傳進(jìn)來的內(nèi)容傳到回調(diào)里.


    //發(fā)生消息,event,生產(chǎn)者
    public static void post(Class type, Object code, Object action) {
        Map<Object, Callback> objectCallbackMap = map.get(type);//判斷這個type有沒有注冊
        if (objectCallbackMap == null) {
            return;
        }
        Callback callback = objectCallbackMap.get(code);//獲取對應(yīng)code的回調(diào)
        if (callback != null) {
            callback.call(action);
        }
    }

全部代碼

public class Event {
    //保存注冊的事件
    private static final Map<Class, Map<Object, Callback>> map = new HashMap<>();

    //發(fā)送event消息,生產(chǎn)者
    public static void post(Class type, Object code, Object action) {
        Map<Object, Callback> objectCallbackMap = map.get(type);//判斷這個type有沒有注冊
        if (objectCallbackMap == null) {
            return;
        }
        Callback callback = objectCallbackMap.get(code);//獲取對應(yīng)code的回調(diào)
        if (callback != null) {
            callback.call(action);
        }
    }

    //注冊事件,回調(diào)就是消費(fèi)者
    public static void register(Class type, Object code, Callback callback) {
        Map<Object, Callback> callbackMap = map.get(type);
        if (callbackMap == null) {//判斷這個type,有沒有被注冊過
            callbackMap = new HashMap<>();
            callbackMap.put(code, callback);//添加code,與回調(diào)
            map.put(type, callbackMap);
        } else {
            callbackMap.put(code, callback);
        }
    }

    /**
     * 事件回調(diào)
     */
    public interface Callback {
        void call(Object o);
    }
}

不扯設(shè)計,實現(xiàn)總結(jié)

其實通俗點(diǎn)講就是:
1.一個單例保存Type和回調(diào)
2.因為是單例,所以其保存的相當(dāng)于全局可見可用
3.所以在取消注冊前(也就是從單例中刪除),相當(dāng)于是全局的,也就會一直存在內(nèi)存中
4.然后就能隨時訪問里面的回調(diào).達(dá)到跨域通信的目的.

一句話:想了一個辦法,能直接訪問需要的內(nèi)存中的某個對象.

至于注解啥的啊,就像昨天寫的,只是加個標(biāo)記方便擴(kuò)展,生成判斷代碼,節(jié)省代碼用的.


交流群:493180098,這是個很少吹水,交流學(xué)習(xí)的群.
APP開發(fā)維護(hù)咨詢?nèi)?: 492685472 ,承接APP迭代.開發(fā)維護(hù).咨詢業(yè)務(wù),付費(fèi)快速解決問題.

最后編輯于
?著作權(quán)歸作者所有,轉(zhuǎn)載或內(nèi)容合作請聯(lián)系作者
【社區(qū)內(nèi)容提示】社區(qū)部分內(nèi)容疑似由AI輔助生成,瀏覽時請結(jié)合常識與多方信息審慎甄別。
平臺聲明:文章內(nèi)容(如有圖片或視頻亦包括在內(nèi))由作者上傳并發(fā)布,文章內(nèi)容僅代表作者本人觀點(diǎn),簡書系信息發(fā)布平臺,僅提供信息存儲服務(wù)。

友情鏈接更多精彩內(nèi)容