1. 耗時操做使用多線程, 耗時操做放在UI線程中會致使用戶的操做沒法獲得響應.android
2. 阻塞操做使用多線程, 理由同上.多線程
3. 多核CUP的設備使用多線程, 能夠有效提升CPU的利用率.函數
4. 並行操做使用多線程.oop
每一個線程最多隻能有一個消息隊列, android中UI線程默認具備消息隊列, 但非UI線程在默認狀況下是不具有消息隊列的. 若是須要在非UI線程中開啓消息隊列, 須要調用Looper.prepare()方法, 在該方法的執行過程當中會建立一個Looper對象, 而Looper的構造函數中會建立一個MessageQueue instance(Looper的構造函數是私有的, 在Looper類以外沒法建立其對象). 此後再爲該線程綁定一個Handler instance, 而後調用Looper.loop()方法, 就能夠不斷的從消息隊列中取出消息和處理消息了. Looper.myLoop()方法能夠獲得線程的Looper對象, 若是爲null, 說明此時該線程還沒有開啓消息隊列.post
1. public Handler(). 建立好的Handler instance將綁定在代碼所在的線程的消息隊列上, 所以必定要肯定該線程開啓了消息隊列, 不然程序將發生錯誤. 使用這個構造函數建立Handler instance, 通常來講, 咱們須要重寫Hanler類的handleMessage()方法, 以便在以後的消息處理時調用.spa
2. public Handler(Callback callback). Callback是Handler內部定義的一個接口, 所以想要使用這個構造函數建立Handler對象, 須要自定義一個類實現Callback接口, 並重寫接口中定義的handleMessage()方法. 這個構造函數其實與無參的構造函數相似, 也要確保代碼所在的線程開啓了消息隊列. 不一樣的是在以後處理消息時, 將調用callback的handleMessage()方法, 而不是Handler對象的handleMssage()方法.線程
3. public Handler(Looper looper). 這個構造函數表示建立一個Handler instance, 並將其綁定在looper所在的線程上. 此時looper不能爲null. 此時通常也須要重寫Hanler類的handleMessage()方法code
4. public Handler(Looper looper, Callback callback). 能夠結合2和3理解.對象
隊列中的每個Message都有一個when字段, 這個字段用來決定Message應該什麼時候出對處理. 消息隊列中的每個Message根據when字段的大小由小到大排列, 排在最前面的消息會首先獲得處理, 所以能夠說消息隊列並非一個嚴格的先進先出的隊列.接口
Message對象能夠經過arg1, arg2, obj字段和setData()攜帶數據, 此外還具備不少字段. when字段決定Message應該什麼時候出對處理, target字段用來表示將由哪一個Handler對象處理這個消息, next字段表示在消息隊列中排在這個Message以後的下一個Message, callback字段若是不爲null表示這個Message包裝了一個runnable對象, what字段表示code, 即這個消息具體是什麼類型的消息. 每一個what都在其handler的namespace中, 咱們只須要確保將由同一個handler處理的消息的what屬性不重複就能夠.
Message對象的target字段關聯了哪一個線程的消息隊列, 這個消息就會被壓入哪一個線程的消息隊列中.
1. 調用Handler類中以send開頭的方法能夠將Message對象壓入消息隊列中, 調用Handler類中以post開頭的方法能夠將一個runnable對象包裝在一個Message對象中, 而後再壓入消息隊列, 此時入隊的Message其callback字段不爲null, 值就是這個runnable對象. 調用Handler對象的這些方法入隊的Message, 其target屬性會被賦值爲這個handler對象.
2. 調用Message對象的sendToTarget()方法能夠將其自己壓入與其target字段(即handler對象)所關聯的消息隊列中.
調用Handler對象中以remove開頭的方法就能夠.
全部在消息隊列中的消息, 都具備target字段. 消息是在target所關聯的線程上被取出和處理的.
1. 若是取出的Message對象的callback字段不爲null, 那麼就調用callback字段的run()方法(callback字段的類型是runnable). 注意此時並不開啓一個新的線程運行run()方法, 而是直接在handler對象(即Message的target字段)所關聯的線程上運行.
2. 若是取出的Message對象的callback字段爲null, 且Handler對象中的callback字段也爲null, 那麼這個消息將由Handler對象的handleMessage(msg)方法處理. 注意Message對象的callback字段是Runnable類型的而Handler對象的callback字段是Callback類型的, Handler對象的callback字段是在建立Handler instance的時候指定的, 若是沒有指定則這個字段爲null, 詳見Handler類的四個構造方法.
3. 若是取出的Message對象的callback字段爲null, 且Handler對象中的callback字段不爲null, 那麼這個消息將由Handler對象中的callback字段的handleMessage方法處理.