一、关于AysncTask
AsyncTask使得多线程编程更加简单,AsyncTask能在后台线程执行异步任务,并且在UI线程更新界面,而不再需要用户去操作Thread和Handler。AysncTask是一个抽象类,类关系如下:
java.lang.Object | |
↳ | android.os.AsyncTask<Params, Progress, Result> |
*AsyncTask适合比较简单的操作(最多几秒钟),如网络请求,如果需要线程运行较长一段时间,建议使用 java.util.concurrent包中的API,例如Executor,ThreadPoolExecutor 和 FutureTask.
二、AsyncTask的使用
一个异步的任务由系统决定运行在一个后台线程,运行结果在UI线程更新。AsyncTask一个异步任务,由一中的类关系可以看到定义了3个泛型类型,分别是Params,Progress 和 Result,另外还定义了4个步骤(方法),分别是onPreExecute,doInBackground, onProgressUpdate 和onPostExecute.
AsyncTask 是抽象类,必须被子类继承后使用,子类必须重写一个方法(doInBackground(Params...)),大多数情况下也会重写另一个方法(onPostExecute(Result).)
我们先看下Android官方提供的示例代码,然后再做解释:
private class DownloadFilesTask extends AsyncTask<URL, Integer, Long> {
protected Long doInBackground(URL... urls) {
int count = urls.length;
long totalSize = 0;
for (int i = 0; i < count; i++) {
totalSize += Downloader.downloadFile(urls[i]);
publishProgress((int) ((i / (float) count) * 100));
// Escape early if cancel() is called
if (isCancelled()) break;
}
return totalSize;
}
protected void onProgressUpdate(Integer... progress) {
setProgressPercent(progress[0]);
}
protected void onPostExecute(Long result) {
showDialog("Downloaded " + result + " bytes");
}
}
三、AsyncTask接收的三个泛型
从示例代码可以看到二中所说的3个参数,下面是官方文档中的解释,下图中展示了3个参数的关系:
1 Params, 后台任务执行所需的数据,如:网络请求的url地址
2 Progress, 后台任务执行距离完成的百分比
3 Result 后台任务执行完成的结果
*以上的三个参数哪个不需要使用的话可用void
四、AsyncTask中的四步(四个方法)
当一个AsyncTask 执行时,会调用以下四步(如二中所说,需要重写doInBackground方法来执行后台代码,其它三个方法都是可选的):
1 onPreExecute() 这步在UI线程中执行,一般用来做后台任务执行前的准备工作,例如在界面显示一个进度条。
2 doInBackground(Params...) 这一步会在onPreExecute()执行完成后立即被执行,即在后台线程中执行耗时的任务。AsyncTask的参数会被传下来,后台任务的执行结果必须在这一步中被return,然后会被传递给最后一步。这一步也可以用publishProgress(Progress...)来更新进度,对应值会传递到在UI线程中执行的onProgressUpdate(Progress...)这一步。
3 onProgressUpdate(Progress...) 这一步会在上一步调用publishProgress(Progress...)后在UI线程执行,用来在用户界面上显示进度。例如,显示一个动态的进度条或者直接在textfiled种显示信息。
4 onPostExecute(Result) 这一步是在后台任务完成后在UI线程执行,后台任务的结果会被作为参数传进来
可以调用 cancel(boolean) 方法来取消一个正在执行的AsyncTask任务。执行这个方法后会使得isCancelled()方法反回true,并且在doInBackground(Object[])执行完成后会调用执行onCancelled(Object)方法而不是onPostExecute(Object)方法。调用cancel(boolean)方法后,并不保证任务马上被取消,为了使得任务被尽快的取消,应该总是周期性地在doInBackground(Object[])中检查isCancelled()的返回值(如二中的官方示例代码)
六、AsyncTask的几天规则
以下是官方指明的使用AsyncTask需要遵从的几条规则:
• AsyncTask类实例必须在UI线程中创建
• execute(Params...)方法必须要在UI线程中调用
•不要手动调用onPreExecute(), onPostExecute(Result), doInBackground(Params...), onProgressUpdate(Progress...)方法
• 一个任务不能被同时执行多次(第二次就会抛出异常)
七、一个简单的Demo示例代码:
实例代码来自:http://samir-mangroliya.blogspot.in/p/android-asynctask-example.html
实例代码下载: http://download.csdn.net/detail/dolacmeng/9336017
Demo执行效果: