這幾天,遇見個奇葩問題,記錄一下。
在用AsyncTask的時候,new 出來的AsyncTask總是等了很久才執行到。
於是乎,想到了是不是前面已經有好幾個AsyncTask的實例了,是不是線程優先級的問題呢?
在了解了以下知識后,發現AsyncTask默認總是先后執行的,除非調用AsyncTask.executeOnExecutor才是並發執行,不過此方法可能造成數據混亂,但是我的AsyncTask本來就是有先后順序,而且有標示,所以以應該不會出現混亂的狀況。
Notes:
1:
因為AsyncTask里面的內部handler和Executor都是靜態變量,所以,他們控制着所有的子類。
2:
我們可以通過AsyncTask.execute()方法來調用系統默認的線程池來處理當前的任務,
系統默認的線程池用的是SerialExecutor.這個線程池控制所有任務按順序執行。也就是一次只執行一條.
當前執行完了,才執行下一條.2.3平台以前是所有的任務並發執行,這會導致一種情況,就是其中一條任務執行出問題了,會引起其他任務出現錯誤.
3:
AsyncTask.executeOnExecutor(AsyncTask.THREAD_POOL_EXECUTOR)你也可以采用這個系統提供的線程池來處理你的任務
默認這個線程池是並發處理任務的,也就是不按順序來.核心為5條,最大128條
4:
你也可以使用自定義的線程池,這樣就可以即使的執行你的任務需求,而不是用系統的。因為用系統默認的線程池可以需要等待,它默認是按順序執行(THREAD_POOL_EXECUTOR)或者最多執行5個(SerialExecutor).
自己使用自定義線程池方式如下:
new AsyncTask.executeOnExecutor((ExecutorService)Executors.newCachedThreadPool()).
5: 不要隨意使用AsyncTask,除非你必須要與UI線程交互.默認情況下使用Thread即可,要注意需要將線程優先級調低.
從google官方文檔你也可以看到,AsyncTasks should ideally be used for short operations (a few seconds at the most.)
AsyncTask適合處理短時間的操作,長時間的操作,比如下載一個很大的視頻,這就需要你使用自己的線程來下載,不管是斷點下載還是其它的.
參考:http://java.chinaitlab.com/base/919389.html