Android:AsyncTask
來源:程序員人生 發(fā)布時(shí)間:2016-05-09 11:27:35 閱讀次數(shù):2542次
AsyncTask是異步任務(wù),在不阻塞UI線程的情況下,在后臺處理復(fù)雜邏輯,并將結(jié)果返回到UI線程,現(xiàn)在來分析1下AsyncTask的實(shí)現(xiàn)。
先來看看我們常見的使用方法。
先聲明1個(gè)類,繼承自AsyncTask。
class MyTask extends AsyncTask{
@Override
protected Integer doInBackground(Void... params) {
// TODO Auto-generated method stub
return null;
}
}
然后使用它
MyTask task;
task = new MyTask();
task.execute();
具體
AsyncTask都做了甚么,1步步看。在
AsyncTask內(nèi)部有兩個(gè)很重要的對象
private final WorkerRunnable
mWorker;
private final FutureTaskmFuture;
先看看WorkerRunnable
private static abstract class WorkerRunnable
implements Callable{
Params[] mParams;
}
WorkerRunnable繼承自Callable,Callable的官方說明是:Callable和Runnable類似,都是可以在另外一個(gè)線程中履行的,但是2者還是有區(qū)分的。
1、Callable的接口方法是call,Runnable是run
2、Callable可以帶返回值,Runnable不行
3、Callable可以捕獲異常,Runnable不行
public interface Callable{
/**
* Computes a result, or throws an exception if unable to do so.
*
* @return computed result
* @throws Exception if unable to compute a result
*/
V call() throws Exception;
}
再看看FutureTask,F(xiàn)utureTask是異步計(jì)算的結(jié)果,繼承關(guān)系是 FutureTask -> RunnableFuture->Runnable, Future,F(xiàn)utureTask內(nèi)部可以判斷任務(wù)的履行狀態(tài),并切可以取消任務(wù)。
FutureTask的構(gòu)造函數(shù)接收1個(gè)Callable類型參數(shù),賦值給callable對象
public FutureTask(Callablecallable) {
if (callable == null)
throw new NullPointerException();
this.callable = callable;
this.state = NEW; // ensure visibility of callable
}
上面的WorkerRunnable被傳入,在FutureTask的run方法中,調(diào)用WorkerRunnable的call方法履行,并返回結(jié)果。
public void run() {
......
try {
Callablec = callable;
if (c != null && state == NEW) {
V result;
boolean ran;
try {
result = c.call();
ran = true;
} catch (Throwable ex) {
......
}
if (ran)
set(result);
}
} finally {
......
}
}
下面就來看看AsyncTask的初始化
public AsyncTask() {
mWorker = new WorkerRunnable
() {
public Result call() throws Exception {
......
}
};
mFuture = new FutureTask(mWorker) {
@Override
protected void done() {
......
}
};
}
我們
看到,之條件到過的兩個(gè)對象,在這里被創(chuàng)建,mFuture實(shí)現(xiàn)了done的重載,就是任務(wù)完成后,履行此處代碼。當(dāng)我們履行execute方法是,調(diào)用的是下面代碼
public final AsyncTask
execute(Params... params) {
return executeOnExecutor(sDefaultExecutor, params);
}
public final AsyncTask executeOnExecutor(Executor exec,
Params... params) {
if (mStatus != Status.PENDING) {
switch (mStatus) {
case RUNNING:
throw new IllegalStateException("Cannot execute task:"
+ " the task is already running.");
case FINISHED:
throw new IllegalStateException("Cannot execute task:"
+ " the task has already been executed "
+ "(a task can be executed only once)");
}
}
mStatus = Status.RUNNING;
onPreExecute();
mWorker.mParams = params;
exec.execute(mFuture);
return this;
}
通過 exec.execute(mFuture); 開始履行任務(wù),
execute需要Runnable類型對象,mFuture就是FutureTask類型對象,繼承自Runnable。
再看看結(jié)果取得后,返回的動(dòng)作。
在FutureTask中的run方法中通過 callable 開始履行任務(wù),任務(wù)結(jié)束后,會履行set方法
public void run() {
......
try {
Callablec = callable;
if (c != null && state == NEW) {
......
if (ran)
set(result);
}
} finally {
......
}
}
set方法中履行結(jié)束任務(wù)的方法 finishCompletion,這里就會調(diào)用 done 接口,就通知到了AsyncTask的mFuture的done回調(diào)
protected void set(V v) {
if (UNSAFE.compareAndSwapInt(this, stateOffset, NEW, COMPLETING)) {
outcome = v;
UNSAFE.putOrderedInt(this, stateOffset, NORMAL); // final state
finishCompletion();
}
}
private void finishCompletion() {
// assert state > COMPLETING;
......
done();
callable = null; // to reduce footprint
}
mFuture的done回調(diào)中會通過postResultIfNotInvoked調(diào)用postResult直接提交結(jié)果,那末對另外一個(gè)對象mWorker來講,在call回調(diào)中,通過postResult(doInBackground(mParams));去提交結(jié)果,所以 doInBackground 是我們必須實(shí)現(xiàn)的1個(gè)接口函數(shù)。
postResult中通過內(nèi)部的1個(gè)handler,去通知UI進(jìn)程,并處理 onPostExecute 及 onProgressUpdate 接口的實(shí)現(xiàn)。這樣就完成了任務(wù)的全部傳遞。
生活不易,碼農(nóng)辛苦
如果您覺得本網(wǎng)站對您的學(xué)習(xí)有所幫助,可以手機(jī)掃描二維碼進(jìn)行捐贈