Android Handler 消息機制+工作原理

我們先來說下

大多數都會這樣回答,一個Handler允許發送和處理Message和Runable對象,UI主線程會自動分配一個Looper(消息輪詢器),每個Looper中封裝着MessageQueue(消息隊列),遵循先進先出原則。Looper負責不斷的從自己的消息隊列裏取出隊頭的任務或消息執行。一般是在子線程執行完耗時操作之後,通過Handler的sendMessage或post方法將Message和Runable對象傳遞給MessageQueue,而且在這些對象離開MessageQueue時,Handler負責執行他們(用到handleMessage方法,主要執行刷新UI的代碼)。那下面我們分析下爲什麼這部分的大多數?

什麼情況下(爲什麼)使用handler?

大家都知道handler是更新於UI界面,當然更新UI界面要在主線程,子線程不支持。而子線程做一些耗時操作得到的數據無法及時更新Ui界面,比如在加載數據+下載圖片等等 需要網絡加載的這些操作都需要耗時,這時候我們需要重新創造一個子線程異步處理耗時操作,這樣就不會堵塞主線程導致卡頓的情況,出現ANR現象。異步處理成功後如果這個時候我們需要更新視圖操作就不能直接更新,這個時候Handler就起到了作用。、

這樣來說我們可以知道 handler一般用於主線程與子線程之間的通訊,主要是用於異步消息的處理。

handler機制是由MessageQueue、Looper來構建和處理的消息機制。我們來單獨說下。

MessageQueue:看名字就能知道這是消息隊列,用來存放線程消息

Looper:消息循環。MessageQueue來存儲消息,Looper則是以無限循環的方式去查找消息。一個線程可以產生一個Looper對象,由它來管理此線程裏的MessageQueue(消息隊列)。

handler通過sendMessage或者post去將消息發送到MessageQueue中,而MessageQueue的next()方法會將消息返回給Looper,Looper接受到的消息就會處理,接着Handler最終調用handlerMessage()來處理消息。

sendMessage(message);                                    //發送消息
sendEmptyMessage(0);                                     //其實內部實現還是和上面一樣
endEmptyMessageAtTime(int what, long uptimeMillis);      //定時發送空消息
sendEmptyMessageDelayed(int what, long delayMillis);     //延時發送空消息
sendMessageAtTime(Message msg, long uptimeMillis);       //定時發送消息
sendMessageDelayed(Message msg, long delayMillis);       //延時發送消息

Handler創建發送以及處理消息。

創建消息

每一個消息需要被指定的Handler處理。android消息機制引入了消息池,Handler創建消息,首選查詢消息池是否有消息存在,如有則直接取出消息,如沒有則創建一個新的消息對象。

消息池的作用,我們使用消息池可以讓消息不被使用時,並不作爲垃圾回收,提高了對消息的複用,減少GC(垃圾回收)的次數。

 

發送消息

UI主線程初始化第一個Handler時候會通過ThreadLocal創建一個Looper;該Looper與UI主線程一一對應,使用ThreadLocal的目的是保證每一個線程值創建唯一一個Looper;之後其他Handler初始化的時候直接獲取第一個Handler創建的Looper。Looper初始化的時候會創建一個消息隊列MessageQueue。

處理消息

UI主線程通過Handler循環查詢消息隊列,當有消息時存在時,就將從消息隊列中取出,通過消息的參數判斷消息對應的handler,將消息分發到指定的Handler進行處理。

 

發表評論
所有評論
還沒有人評論,想成為第一個評論的人麼? 請在上方評論欄輸入並且點擊發布.
相關文章