1、線程間通信的Message機制java
一、Message介紹android
frameworks\base\core\java\android\Os\Message.java函數
Message是線程之間傳遞信息的載體,包含了對消息的描述和任意的數據對象。Message中包含了兩個額外的 int字段和一個object字段,這樣在大部分狀況下,使用者就不須要再作內存分配工做了。雖然Message的構造函數是public的,可是最好是使用Message.obtain( )或Handler.obtainMessage( )函數來獲取Message對象,由於Message的實現中包含了回收再利用的機制,能夠提供效率。oop
二、MessageQueue介紹post
frameworks\base\core\java\android\Os\MessageQueue.javaspa
MessageQueue用來容納Message隊列的,其中的Message是由Looper來分發的,Message不能直接添加到MessageQueue中,而是要經過與Looper關聯的Handler去添加。線程
三、Loopercode
frameworks\base\core\java\android\Os\Looper.java對象
Looper是線程用來運行消息循環的。線程自己是沒有消息循環的,須要在線程中調用perpare函數,而後調用loop去處理消息。在Android中,系統在啓動主線程的時候會自動爲之創建一個Looper。繼承
創建本線程的Looper:
public static final void prepare()
運行本線程的Looper:
public static final void loop()
獲取本線程的Looper:
public static final Looper myLooper()
獲取主線程的Looper:
public synchronized static final Looper getMainLooper()
四、Handler
frameworks\base\core\java\android\Os\Handler.java
Handler是用來發送和處理與線程相關聯的Message和Runnable對象的。每一個Handler都與一個單獨的線程以及線程消息隊列相關聯的。當你建立Handler時,Handler就與線程以及線程消息隊列綁定了,從那之後,Handler就能夠將 Message和Runnable發送給對應的消息隊列,而且可以處理從消息隊列中出來的消息。
Handler提供了用戶須要調用的大部分接口
A、建立Handler:
建立與本地線程相關聯的Handler:
1 |
public Handler() |
2 |
3 |
public Handler(Callback callback) |
建立與指定線程相關聯的Handler:
1 |
public Handler(Looper looper) |
2 |
3 |
public Handler(Looper looper, Callback callback) |
B、建立消息
1 |
public final Message obtainMessage() |
2 |
3 |
public final Message obtainMessage( int what) |
4 |
5 |
public final Message obtainMessage( int what, Object obj) |
6 |
7 |
public final Message obtainMessage( int what, int arg1, int arg2) |
8 |
9 |
public final Message obtainMessage( int what, int arg1, int arg2, Object obj) |
C、刪除消息
刪除在消息隊列中未處理的消息
1 |
public final void removeMessages( int what) |
2 |
3 |
public final void removeMessages( int what, Object object) |
D、發送消息
1 |
public final boolean sendMessage(Message msg) |
2 |
3 |
public final boolean sendMessageDelayed(Message msg, long delayMillis) |
4 |
5 |
public final boolean post(Runnable r) |
6 |
7 |
public final boolean postDelayed(Runnable r, long delayMillis) |
E、處理消息
在Looper的loop函數中循環取出MessageQueue的接收消息隊列中的消息,而後調用Hander的dispatchMessage函數對消息進行處理,至於如何處理(相應消息)則由用戶指定(三個方法,優先級從高到低:Message裏面的Callback,一個實現了Runnable接口的對象,其中run函數作處理工做;Handler裏面的mCallback指向的一個實現了Callback接口的對象,裏面的handleMessage進行處理;處理消息 Handler對象對應的類繼承並實現了其中handleMessage函數,經過這個實現的handleMessage函數處理消息)。
01 |
public void dispatchMessage(Message msg) { |
02 |
03 |
if (msg.callback != null ) { |
04 |
05 |
handleCallback(msg); |
06 |
07 |
} else { |
08 |
if (mCallback != null ) { |
09 |
if (mCallback.handleMessage(msg)) { |
10 |
return ; |
11 |
} |
12 |
} |
13 |
14 |
handleMessage(msg); |
15 |
} |
16 |
} |
2、Message機制的用途
Message機制有兩種用途:
定時執行:延遲到指定時間執行消息調度
線程通信:將某些操做在其餘線程中排隊執行
一、定時執行
經過本線程的Handler將消息延遲到指定時間執行,至關於定時器的做用
1 |
public final boolean sendMessageDelayed(Message msg, long delayMillis) |
2 |
3 |
public final boolean postDelayed(Runnable r, long delayMillis) |
還能夠在指定時間到期以前,經過removeMessages取消執行
二、線程通信
Android的UI是單線程的,Android但願UI線程可以給予User快速的反應,若是UI線程花費太多的時間作幕後的事情,吵過5秒鐘,Android就會給出錯誤提示。所以爲了不拖住UI,一下較費時的工做應該交給獨立的線程去執行。可是若是幕後的線程來執行UI對象,Android又會發出錯誤信息,因此UI線程與幕後線程須要進行通信。UI線程將工做分發給幕後線程,幕後線程執行後將相應的狀態返回給UI線程,讓UI線程對UI作成相應的更新。