實現線程:繼承Thread類或者實現Runnable接口ide
因爲Handler運行在主線程中(UI線程中), 它與子線程能夠經過Message對象來傳遞數據, 這個時候,Handler就承擔着接受子線程傳過來的(子線程用sedMessage()方法傳弟)Message對象,(裏面包含數據) , 把這些消息放入主線程隊列中,配合主線程進行更新UI。函數
handler能夠分發Message對象和Runnable對象到主線程中, 每一個Handler實例,都會綁定到建立他的線程中(通常是位於主線程),oop
Android系統的應用程序是消息驅動的,系統會爲每個應用程序配備一個消息隊列,當應用程序運行的時候,該應用程序的主線程會不斷的查看消息隊列看看有沒有消息要處理。post
===================================================================spa
回調函數Run()執行完,線程終止,因此若是你要讓線程不斷的作一些耗時的事情的時候,你應該在回調函數裏整一個循環。線程
===================================================================對象
建立線程的兩種方法:blog
1.直接繼承Thread,重寫run()函數繼承
Public class MyThread extends Thread{接口
@override
public void run(){
//線程的實現體
}
}
New MyThread().start();
2.實現接口Runnable
Public Class MyRunnable implements Runnable{
@override
public void run(){
//線程的實現體
}
}
New Thread(new MyRunnable()).start();
兩種方法的比較:其實兩種方法從源碼上來看本質是同樣,都是調用了create(ThreadGroup group, Runnable runnable, String threadName, long stackSize)函數,只是兩種方法再調用的時候傳遞的參數不同,
直接繼承Thread類的方法:create(null, null, threadName, 0);
實現Runnable接口的方法:create(group, runnable, threadName, 0);
主要區別在於第二個參數,若是爲空表示線程的執行方法爲繼承Thread的類的回調函數run(),若是爲runnable,表示線程的執行方法爲Runnable的run()方法。
===================================================================
Android中更新UI的操做必須放在被更新的UI的Root線程中,即建立它的線程中。
Android提供了兩種事件處理機制:基於監聽器的事件處理、基於回調函數的事件處理。
Runnable 到底是什麼?
Runnable 其實只是一個普通的接口,它帶有一個抽像函數run(),僅此而已。Runnable不是線程,只是咱們可使用Runnable來做爲參數建立線程,咱們知道建立線程的兩種方法:一是MyThreadObject.start() 另一種是Thread(MyRunnable).Start()。
所以來看下面的代碼:
剛開始是的誤解:
1.handler 實現UI更新的原理
2.建立labelTimer控件的線程是主線程,這裏(劃紅線的部分)不是子線程來更新主線程建立的控件嗎?怎麼不會出錯?
解答疑問一:
Handler一直在main thread中執行,有一個不斷循環的Looper,不斷檢索一個容器MessageQueue,這個容器,一旦有Message進來就去執行這個Message,若是這個Message有callback(一個Runnable,若是是handler.post(runnable)的話, 會生成一個Message對象,這個對象的callback參數被賦值成這個runnable對象),那麼也去執行這個callback(也就是runnable對象)的run方法(這個就很相似我上面例子中的Test類中的Say方法了,僅僅只是調用這個run方法而已,不是去開線程).
解答疑問二:
Runnable只是一個普通的接口,建立Runnable匿名內部類時這時候當前的線程仍是主線程。