推薦大家使用AsyncTask代替Thread+Handler的方式,不僅調用上更爲簡單,經過實測更可靠一些,Google在Browser中大量使用了異步任務作爲處理耗時的I/O操作,比如下載文件、讀寫數據庫等等,它們在本質上都離不開消息,但是AsyncTask相比Thread加Handler更爲可靠,更易於維護,但AsyncTask缺點也是有的比如一旦線程開啓即dobackground方法執行後無法給線程發送消息,僅能通過預先設置好的標記來控制邏輯,當然可以通過線程的掛起等待標誌位的改變來通訊,對於某些應用Thread和Handler以及Looper可能更靈活。
這兩種異步處理方法中,其中AsyncTask這個類感覺使用比較簡單,就是實現其中幾個方法,onPreExecute()方法是在任務剛開始運行時執行的一些初始化操作,比如初始化一個進度條等等,然後就執行doInBackground()方法這裏面主要放業務操作,比如查詢數據庫等,在這個方法執行的時候會調用onProgressUpdate(),可以在這個方法中更新UI界面,最後是調用onPostExecute()方法,當得到業務結果後就可以在這個方法中返回給UI線程,也可以關閉一些執行這個業務時開的一些資源。大家可以看得出AsyncTask這個類是一個泛型類,這個類的三個參數以此對應doInBackground(String... params),onProgressUpdate(String... values),onPostExecute(String result)的參數,很形象的···如果不需要傳參和返回值,可以用Void代替。而doInBackground(String... params)方法的返回值也就是onPostExecute(String result)方法的參數值,因爲doInBackground方法執行後返回的值是在onPostExecute(String result)中處理的。
用handler方式處理需要知道與handler相關的幾個組件,Looper和Queue,其實Looper的作用就是把handler發送的消息放到Queue中,並把消息廣播給所有與這個Queue相關的handler,而Queue一般是主線程開啓的時候就給這個線程分配了一個,所以你要與UI主線程通信必須用於這個Queue相關聯的handler對象才行,一般handler對象在那個線程中創建的就與那個線程的queue關聯,所以在UI線程中創建的handler對象就與UI線程通訊,這樣我們就可以在子線程中發送消息給主線程,實現更新UI的功能。那主線程又是怎麼處理子線程發送的消息的呢?其實在生成handler對象的時候我們就要實現handler對象的handleMessage()方法這個方法就是主線程接受並處理子線程發送過來的消息的方法,從而實現
更新UI線程的功能。
簡單示例:
private Handler handler = new Handler() {
@Override
public void handleMessage(Message msg) {
switch (msg.what) {
case 1:
adapter.notifyDataSetChanged();
break;
}
}
};
public void onCreate(Bundle savedInstanceState) {
super.onCreate(savedInstanceState);
showContent();
}
private void showContent() {
listView = (ListView) findViewById(R.id.journals_list_one);
// MyTask myTask = new MyTask();
// myTask.execute(null);
new Thread() {
@Override
public void run() {
try {
Thread.sleep(5000);
loadData();
} catch (InterruptedException e) {
e.printStackTrace();
}
}}.start();
adapter = new JournalListAdapter(this, data);
listView.setAdapter(adapter);
}
/**
* 構造List列表數據
*/
private void loadData() {
if (data.size() <= 40) {
for (int i = 0; i < 10; i++) {
Map<String, String> map = new HashMap<String, String>();
map.put("title", getString(R.string.title));
map.put("desc", getString(R.string.content));
data.add(map);
Message message = handler.obtainMessage();
message.what = 1;
message.sendToTarget();
}
}
}
class MyTask extends AsyncTask<String, String, String> {
private ProgressDialog progressBar;
@Override
protected void onPreExecute() {
progressBar = new ProgressDialog(MainPageActivity.this);
progressBar.setMessage("正在加載數據請稍後...");
progressBar.setIndeterminate(true);
progressBar.show();
super.onPreExecute();
}
@Override
protected String doInBackground(String... params) {
try {
Thread.sleep(5000);
loadData();
} catch (InterruptedException e) {
e.printStackTrace();
}
return null;
}
@Override
protected void onProgressUpdate(String... values) {
super.onProgressUpdate(values);
adapter.notifyDataSetChanged();
}
@Override
protected void onPostExecute(String result) {
super.onPostExecute(result);
progressBar.dismiss();
}
}