AsyncTask

new AsyncTask<String,String,String>(){
// 运行在主线程中,做预备工作
onPreExecute(){ }
// 运行在子线程中,做耗时操作
String doingBackGround(String s){ }
// 运行在主线程中,耗时操作完成,更新UI
onPostExecute(String s){ } }.execute(String);

AsyncTask的execute方法

public final AsyncTask<Params, Progress, Result> execute(Params... params) {
... mStatus = Status.RUNNING;
// 在主线程中执行准备操作
onPreExecute();
// 把params参数赋值给mWorker
mWorker.mParams = params;
// 用线程池执行mFuture
sExecutor.execute(mFuture); // 在AsyncTask构造方法中创建了mWorker
mWorker = new WorkerRunnable<Params, Result>() {
public Result call() throws Exception {
...
}
}; mFuture = new FutureTask<Result>(mWorker) {
@Override
protected void done() {
...
}
};
}
// 把mWorker传递给FutureTask,callable指的就是mWorker
public FutureTask(Callable<V> callable) {
if (callable == null)
throw new NullPointerException();
sync = new Sync(callable);
}
// 把mWorker传递给Sync,callable指的是mWorker
Sync(Callable<V> callable) {
this.callable = callable;
}

线程池执行FutureTask,就是执行FutureTask的run方法,代码如下:

    public void run() {
// 转调
sync.innerRun();
} void innerRun() {
if (!compareAndSetState(READY, RUNNING))
return; runner = Thread.currentThread();
if (getState() == RUNNING) { // recheck after setting thread
V result;
try {
// 就是调用了mWorker.call方法
// 把耗时操作得到的结果赋值给result
result = callable.call();
} catch (Throwable ex) {
setException(ex);
return;
}
// 转调了sync.innerSet(v);
set(result);
} else {
releaseShared(0); // cancel
}
} mWorker = new WorkerRunnable<Params, Result>() {
public Result call() throws Exception {
Process.setThreadPriority(Process.THREAD_PRIORITY_BACKGROUND);
// 执行耗时操作 在子线程中执行
return doInBackground(mParams);
}
}; protected void set(V v) {
// 转调
sync.innerSet(v);
} void innerSet(V v) {
for (;;) {
int s = getState();
if (s == RAN)
return;
if (s == CANCELLED) {
// aggressively release to set runner to null,
// in case we are racing with a cancel request
// that will try to interrupt runner
releaseShared(0);
return;
}
if (compareAndSetState(s, RAN)) {
result = v;
releaseShared(0);
// 调用了FutureTask的抽象方法
done();
return;
}
}
} mFuture = new FutureTask<Result>(mWorker) {
@Override
protected void done() {
Message message;
Result result = null; try {
// 转调了sync.innerGet()
result = get();
} catch (InterruptedException e) {
android.util.Log.w(LOG_TAG, e);
} catch (ExecutionException e) {
throw new RuntimeException("An error occured while executing doInBackground()",
e.getCause());
} catch (CancellationException e) {
message = sHandler.obtainMessage(MESSAGE_POST_CANCEL,
new AsyncTaskResult<Result>(AsyncTask.this, (Result[]) null));
message.sendToTarget();
return;
} catch (Throwable t) {
throw new RuntimeException("An error occured while executing "
+ "doInBackground()", t);
}
// 发送了一个Message
message = sHandler.obtainMessage(MESSAGE_POST_RESULT,
new AsyncTaskResult<Result>(AsyncTask.this, result));
message.sendToTarget();
}
}; public V get() throws InterruptedException, ExecutionException {
// 转调
return sync.innerGet();
} V innerGet() throws InterruptedException, ExecutionException {
acquireSharedInterruptibly(0);
if (getState() == CANCELLED)
throw new CancellationException();
if (exception != null)
throw new ExecutionException(exception);
// 把之前doinBackground方法的结果返回
return result;
}

在AsyncTask的成员变量,创建了InternalHandler

private static class InternalHandler extends Handler {
@SuppressWarnings({"unchecked", "RawUseOfParameterizedType"})
@Override
public void handleMessage(Message msg) {
AsyncTaskResult result = (AsyncTaskResult) msg.obj;
switch (msg.what) {
case MESSAGE_POST_RESULT:
// There is only one result
// 结束耗时操作完成后的消息
// 调用了AsyncTask的finish方法传递的result.mData[0]就是之前
// 耗时操作返回来的结果
result.mTask.finish(result.mData[0]);
break;
case MESSAGE_POST_PROGRESS:
result.mTask.onProgressUpdate(result.mData);
break;
case MESSAGE_POST_CANCEL:
result.mTask.onCancelled();
break;
}
}
}
private static class AsyncTaskResult<Data> {
final AsyncTask mTask;
final Data[] mData;
// data 是返回的结果
AsyncTaskResult(AsyncTask task, Data... data) {
mTask = task;
mData = data;
}
} private void finish(Result result) {
if (isCancelled()) result = null;
// 耗时操作完成,更新UI,执行在主线程
onPostExecute(result);
mStatus = Status.FINISHED;
}

源码篇——AsyncTask机制的更多相关文章

  1. 鸿蒙内核源码分析(调度机制篇) | 任务是如何被调度执行的 | 百篇博客分析OpenHarmony源码 | v7.07

    百篇博客系列篇.本篇为: v07.xx 鸿蒙内核源码分析(调度机制篇) | 任务是如何被调度执行的 | 51.c.h .o 任务管理相关篇为: v03.xx 鸿蒙内核源码分析(时钟任务篇) | 触发调 ...

  2. 源码篇:SDWebImage

    攀登,一步一个脚印,方能知其乐 源码篇:SDWebImage 源码来源:https://github.com/rs/SDWebImage 版本: 3.7 SDWebImage是一个开源的第三方库,它提 ...

  3. springMVC源码分析--异常处理机制HandlerExceptionResolver执行原理(二)

    上一篇博客springMVC源码分析--异常处理机制HandlerExceptionResolver简单示例(一)中我们简单地实现了一个异常处理实例,接下来我们要介绍一下HandlerExceptio ...

  4. Dubbo 源码分析 - SPI 机制

    1.简介 SPI 全称为 Service Provider Interface,是 Java 提供的一种服务发现机制.SPI 的本质是将接口实现类的全限定名配置在文件中,并由服务加载器读取配置文件,加 ...

  5. MyBatis 源码分析 - 插件机制

    1.简介 一般情况下,开源框架都会提供插件或其他形式的拓展点,供开发者自行拓展.这样的好处是显而易见的,一是增加了框架的灵活性.二是开发者可以结合实际需求,对框架进行拓展,使其能够更好的工作.以 My ...

  6. spring-boot-2.0.3启动源码篇二 - run方法(一)之SpringApplicationRunListener

    前言 Springboot启动源码系列还只写了一篇,已经过去一周,又到了每周一更的时间了(是不是很熟悉?),大家有没有很期待了?我会尽量保证启动源码系列每周一更,争取不让大家每周的期望落空.一周之中可 ...

  7. spring-boot-2.0.3启动源码篇 - 阶段总结

    前言 开心一刻 朋友喜欢去按摩,第一次推门进来的是一个学生美眉,感觉还不错:后来经常去,有时是护士,有时是空姐,有时候是教师.昨天晚上推门进去的是一个女警察,长得贼好看,身材也很好,朋友嗷的一声就扑上 ...

  8. MySQL Master High Available 源码篇

    https://m.aliyun.com/yunqi/users/1287368569594542/articles https://yq.aliyun.com/articles/59233 MySQ ...

  9. MyBatis 源码篇-整体架构

    MyBatis 的整体架构分为三层, 分别是基础支持层.核心处理层和接口层,如下图所示. 基础支持层 反射模块 该模块对 Java 原生的反射进行了良好的封装,提供了更加简洁易用的 API ,方便上层 ...

随机推荐

  1. [LeetCode] Diameter of Binary Tree 二叉树的直径

    Given a binary tree, you need to compute the length of the diameter of the tree. The diameter of a b ...

  2. mysql 免安装与 忘记root密码 密码过期

    免安装: 参考 :https://blog.csdn.net/werwqerwerwer/article/details/52919939 注:别忘了配置环境变量   忘记root密码解决办法: 1. ...

  3. python3+dlib人脸识别及情绪分析

    一.介绍 我想做的是基于人脸识别的表情(情绪)分析.看到网上也是有很多的开源库提供使用,为开发提供了很大的方便.我选择目前用的比较多的dlib库进行人脸识别与特征标定.使用python也缩短了开发周期 ...

  4. ●SPOJ 1811 Longest Common Substring

    题链: http://poj.org/problem?id=2774 题解: 求两个字符串(S,T)的最长公共子串.对 S串建后缀自动机.接下来就用这个自动机去求出能和 S串匹配的 T的每一个前缀的最 ...

  5. poj 2425 AChessGame(博弈)

    A Chess Game Time Limit: 3000MS   Memory Limit: 65536K Total Submissions: 3791   Accepted: 1549 Desc ...

  6. MFC程序设计小结

    由于毕业设计要用到MFC,因此本人这段时间开始学习MFC编程,边学边做,现将一些重要的知识点总结如下: 创建一个MFC程序,操作步骤很简单,要点就是选择MFC AppWizard(exe).单文档或者 ...

  7. Chinese-Text-Classification:Tensorflow CNN 模型实现的中文文本分类器[不分词版]

    从现在的结果来看,分词的版本准确率稍微高一点. 训练过程: 模型评估: 实验三,准备换一下数据集,用这里的数据集来跑这个模型:https://zhuanlan.zhihu.com/p/30736422 ...

  8. Java 实现32位MD5加密

    MD5介绍[链接] Java代码实现 public class Md5Util { private String Md5Util(String s) { try { MessageDigest md ...

  9. Python开发——利用正则表达式实现计算器算法

    Python开发--利用正则表达式实现计算器算法 (1)不使用eval()等系统自带的计算方法 (2)实现四则混合运算.括号优先级解析 思路: 1.字符串预处理,将所有空格去除 2.判断是否存在括号运 ...

  10. kibana使用

    最近,被老大叫写一个kibana的使用方法给所有人用. 注意的一点: 能不用空格表示OR或者AND就不用空格表示,因为要么全用要么全部不用,否则会因为解析搜索同级的时候,若出现空格和OR,会冲突覆盖意 ...