Handler
在 Android
中負(fù)責(zé)發(fā)送和處理消息祥山,通過(guò)它可以實(shí)現(xiàn)不同線程之間的消息通信往史。
每個(gè) Handler
都需要綁定一個(gè) Looper
來(lái)管理消息隊(duì)列和消息循環(huán)。
Activity
被創(chuàng)建時(shí)就默認(rèn)創(chuàng)建了 Looper
摄咆,所以在主線程中默認(rèn)可以直接使用 Handler
昨凡。這時(shí) Handler
綁定的是 Activity
的 Looper
。
當(dāng)然也可以設(shè)置其他的 Looper
童芹,如果沒(méi)有指定 Looper
,默認(rèn)使用 new Handler()
時(shí)線程所持有的 Looper
鲤拿。
如果當(dāng)前線程沒(méi)有創(chuàng)建 Looper
假褪,就會(huì)報(bào)錯(cuò)。
HandlerThread
HandlerThread
繼承自 Thread
近顷,本質(zhì)就是個(gè) Thread
生音。
其與普通 Thread
的區(qū)別在于實(shí)現(xiàn)了自己的 Looper
,可以單獨(dú)分發(fā)和處理消息窒升。
用來(lái)實(shí)現(xiàn)線程間的通信缀遍,主要是子線程和子線程間的通信。 Handler
更多的主要是子線程到主線程饱须。
HandlerThread 的使用
有時(shí)候需要 Handler
收到消息時(shí)域醇,在子線程處理消息。如果每次都通過(guò) new Thread()
的方式來(lái)新開一個(gè)子線程蓉媳,會(huì)浪費(fèi)資源譬挚,增加系統(tǒng)開銷。
Handler
可以指定 Looper
,但是需要自己處理 Looper
會(huì)比較麻煩酪呻,所以谷歌封裝了 HandlerThread
類减宣。
類似的類有 AsyncTask
。
HandlerThread
處理任務(wù)是串行執(zhí)行玩荠,按消息發(fā)送順序進(jìn)行處理漆腌。
1. 創(chuàng)建
private HandlerThread mHandlerThread;
......
mHandlerThread = new HandlerThread("MyHandlerThread");
handlerThread.start();
HandlerThread
在調(diào)用 start()
方法之后,就可以獲取到子線程的 Looper
阶冈。
2. Handler 中使用 mHandlerThread.getLooper()
mHandler = new Handler(mHandlerThread.getLooper()) {
@Override
public void handleMessage(Message msg) {
System.out.println("收到消息 : " + Thread.currentThread());
}
};
給 mHandler
指定 mHandlerThread
線程中的 Looper
闷尿。
3. 在子線程使用 mHandler
發(fā)送消息,mHandler
中接收和處理消息(也是非 UI
線程)
new Thread(new Runnable() {
@Override
public void run() {
try {
Thread.sleep(1000);//模擬耗時(shí)操作
System.out.println("發(fā)送消息 : " + Thread.currentThread());
mHandler.sendEmptyMessage(0);
} catch (InterruptedException e) {
e.printStackTrace();
}
}
}).start();
4. 釋放
@Override
protected void onDestroy() {
super.onDestroy();
if (mHandlerThread != null) {
mHandlerThread.quitSafely();
}
}
運(yùn)行后的打友廴堋:
System.out: 發(fā)送消息 : Thread[Thread-7,5,main]
System.out: 收到消息 : Thread[MyHandlerThread,5,main]