昨天写的图片的三级缓存,假设有兴趣,能够去看下,浅谈图片载入的三级缓存原理(一)

http://blog.csdn.net/wuyinlei/article/details/50606455

在里面我们下载的时候。採用了AsyncTask异步下载机制,那么今天就来浅谈一下AsycnTask工作机制吧。

首先我们来看下AsyncTask的官方解释

  • AsyncTask is designed to be a helper class around Thread and Handler and does not constitute a generic threading framework. AsyncTasks should ideally be used for short operations (a few seconds at the most.) If you need to keep threads running for long periods of time, it is highly recommended you use the various APIs provided by the java.util.concurrent package such as Executor, ThreadPoolExecutor and FutureTask.
  • AsyncTask的设计是环绕主题和Handler一个辅助类,并不构成通用线程框架。异步任务最好应(至多几秒钟。)可用于短期操作。假设您须要保持对长时间运行的线程。强烈建议您使用java.util.concurrent包等提供的各种API作为遗嘱运行人。并ThreadPoolExecutor的FutureTask提供。

    (英文不太好,google翻译的哈)

  • An asynchronous task is defined by a computation that runs on a background thread and whose result is published on the UI thread. An asynchronous task is defined by 3 generic types, called Params, Progress and Result, and 4 steps, called onPreExecute, doInBackground, onProgressUpdate and onPostExecute.
  • AsyncTask是定义异步任务在后台线程(子线程中)运行的。而结果更新UI在UI线程中,接收三个參数,Params(传入的值)Progress(进度) Result(返回的结果)。有四步onPreExecute(在UI线程中运行,准备操作)doInBackground(子线程中耗时操作)onProgressUpdate (进度更新)onPostExecute(结果返回)

    使用方法我就不解释了。能够去官网看下使用方法,这里仅仅说明异步机制。

好了,那我们就来看下源代码运行的操作吧。首先我们从刚開始出发,也就是execute()。

 new MyAsync().execute(imageView,url);

AsyncTask的execute()方法:

 This method must be invoked on the UI thread.(必须在UI线程中调用)
@MainThread
public final AsyncTask<Params, Progress, Result> execute(Params... params) {
//在这里调用了executeOnExecutor()方法
return executeOnExecutor(sDefaultExecutor, params);
}

来看下executeOnExecutor()方法:

 @MainThread(主线程中调用的)
public final AsyncTask<Params, Progress, Result> executeOnExecutor(Executor exec,
Params... params) {
//这里有一些异常的推断 。因为代码量多。我就去掉了,在这里我们不考虑异常问题 //在这里首先吧状态给位RUNNING
mStatus = Status.RUNNING;
//运行前的准备工作
onPreExecute();
//这里的params就是我们传入的值,然后赋值给了mWorker,那么我们就要看看这个是什么意思了
mWorker.mParams = params;
//用线程池运行这个future
exec.execute(mFuture);
//终于返回自己
return this;
}

mWorker參数的构造:

/**
* Creates a new asynchronous task. This constructor must be invoked on the UI thread.
*/
public AsyncTask() {
//在构造方法中创建mWorker
mWorker = new WorkerRunnable<Params, Result>() {
//这种方法,一会会用到
public Result call() throws Exception {
mTaskInvoked.set(true); //设置线程优先级
Process.setThreadPriority(Process.THREAD_PRIORITY_BACKGROUND);
//noinspection unchecked
//在这里运行耗时操作,传入我们传入的參数,告诉他要干什么
Result result = doInBackground(mParams);
Binder.flushPendingCommands();
//这个得有值的时候运行
return postResult(result);
}
};

FutureTask中的方法调用:

//然后传递给这个类,把mWorker当做參数传递给FutureTask。
mFuture = new FutureTask<Result>(mWorker) {
@Override
protected void done() {
//一些异常处理
};
}

那么我们来看下FutureTask这个类做了些什么(接受到mWorker之后):

 public FutureTask(Callable<V> callable) {
if (callable == null)
throw new NullPointerException();
//把mWorker传递给了callable,那么接下来就得看看callable在做什么了
this.callable = callable;
//状态更新
this.state = NEW; // ensure visibility of callable
}
public void run() {
if (state != NEW ||
!U.compareAndSwapObject(this, RUNNER, null, Thread.currentThread()))
return;
try { //在这里把mWorker给了Callable
Callable<V> c = callable;
if (c != null && state == NEW) {
//这里的V就是一个结果的返回类型
V result;
boolean ran;
try { //事实上就是mWorker.call() 把耗时操作得到的结果给了result
result = c.call();
ran = true;
} catch (Throwable ex) {
result = null;
ran = false;
setException(ex);
}
if (ran) //得到result结果,传递给set方法。调用set方法
set(result);
}
} //异常处理
}

set(result) 方法运行:

//Sets the result of this future to the given value unless
* this future has already been set or has been cancelled.
* 把结果也就是future当做參数传递进去。除非这个已经传了或者任务被取消
* /
protected void set(V v) {
if (U.compareAndSwapInt(this, STATE, NEW, COMPLETING)) { //在这,把result结果给了outcome。
//传递给outcome
outcome = v;
U.putOrderedInt(this, STATE, NORMAL); // final state
finishCompletion();
}
}

那么接下来就把result给了outcome,我们来看下这个是什么吧:

是一个object对象
private Object outcome; //在这里把result传递给了x(object对象)
Object x = outcome; if (s == NORMAL)
//返回future
return (V)x;
if (s >= CANCELLED)
throw new CancellationException();
throw new ExecutionException((Throwable)x);
}

这个时候我们就得到了mFuture对象,我们看看这个干了些什么:


//因为V就是result,在这里把返回的结果传入。然后运行done()方法
mFuture = new FutureTask<Result>(mWorker) {
@Override
protected void done() {
//异常
};
        我们看下mFUture做的什么了
//在这里对mFuture进行了get()方法的回调
public final Result get() throws InterruptedException, ExecutionException {
//在这里又调用了FutureTask里面的方法
return mFuture.get();

FutureTask里面的get()方法:

 /**
* @throws CancellationException {@inheritDoc}
*/
public V get() throws InterruptedException, ExecutionException {
int s = state; //得到当前的状态
if (s <= COMPLETING)
s = awaitDone(false, 0L);
//把当前状态传递给report中
return report(s);
}

我们能够看到在get方法中。最后返回了report(s),那就继续跟进去:

  /**
* Returns result or throws exception for completed task.
*
* @param s completed state value
*/
@SuppressWarnings("unchecked")
private V report(int s) throws ExecutionException {
Object x = outcome;
if (s == NORMAL) //直接return回了result 也就是callable.call()方法的结果,或者说是mWorker.call()方法,把DoInBackground()方法返回
return (V)x;
if (s >= CANCELLED)
throw new CancellationException();
throw new ExecutionException((Throwable)x);
}

这里我们就得到了结果result:

//
mWorker = new WorkerRunnable<Params, Result>() {
public Result call() throws Exception {
mTaskInvoked.set(true); Process.setThreadPriority(Process.THREAD_PRIORITY_BACKGROUND);
//noinspection unchecked //在这里运行了耗时操作
Result result = doInBackground(mParams);
Binder.flushPendingCommands(); //调用postResult()这种方法,开启了子线程,把结果传了进去
return postResult(result);
}
};

看下postResult(result)方法:

 private Result postResult(Result result) {
@SuppressWarnings("unchecked")
//在这里得到的message。然后发出 发送了 MESSAGE_POST_RESULT
Message message =
//发送消息
getHandler().obtainMessage(MESSAGE_POST_RESULT,
//this就是AsyncTask
new AsyncTaskResult<Result>(this, result));
message.sendToTarget();
//返回result
return result;
}

AsyncTaskResult(this,result)方法:

 @SuppressWarnings({"RawUseOfParameterizedType"})
private static class AsyncTaskResult<Data> {
final AsyncTask mTask;
final Data[] mData; //这里的data。就是我们返回的结果
AsyncTaskResult(AsyncTask task, Data... data) {
mTask = task;
mData = data;
}
}

我们看下getHandler()方法:


//在这里创建了handler
private static Handler getHandler() {
synchronized (AsyncTask.class) {
if (sHandler == null) {
//在这里new 除了一个handler
sHandler = new InternalHandler();
}
//返回一个handler对象
return sHandler;
}
}

我们看下InternalHandler()方法:

//继承handler,在这里创建了handler
private static class InternalHandler extends Handler {
public InternalHandler() {
super(Looper.getMainLooper());
} @SuppressWarnings({"unchecked", "RawUseOfParameterizedType"})
@Override
public void handleMessage(Message msg) {
AsyncTaskResult<?> result = (AsyncTaskResult<? >) msg.obj;
switch (msg.what) {
case MESSAGE_POST_RESULT:
//匹配到MESSAGE_POST_RESULT 。在这里处理结果
//接受耗时操作完毕后传递的消息
// There is only one result
//调用了asynctask的finish()方法,传递的值就是之前耗时操作返回的结果
result.mTask.finish(result.mData[0]);
break;
case MESSAGE_POST_PROGRESS:
result.mTask.onProgressUpdate(result.mData);
break;
}
}
}

最后调用finish()方法:

private void finish(Result result) {
if (isCancelled()) {
//取消
onCancelled(result);
} else {
//调用了主线程,耗时操作已经完毕。更新UI,在主线程中运行
onPostExecute(result);
}
//在这里把状态改为FINISHED
mStatus = Status.FINISHED;
}

在这里,耗时操作就已经所有完毕了,状态也改为了FINISHED。到此为止。异步完毕。

  • AsyncTask工作机制也就这么多了。

    当然我们仅仅是考虑了正确工作的状态,也就是请求成功的哈,异常的,取消的,中断的在这里并没有做出解释。

    相信大家去看下源代码也是能够晓得原理的。

  • 因为小弟才疏学浅,也仅仅能简单的走一下源代码。自己理解有限。有些地方凝视的过于简单,希望大家谅解,假设有独特的,好的解释,希望大神们能够赐教一下。在这里小弟不胜感激。(QQ:1069584784)

AsyncTask工作机制简介的更多相关文章

  1. Java NIO工作机制简介

    前言 本博客只简单介绍NIO的原理实现和基本工作流程 I/O和NIO的本质区别 NIO将填充和提取缓冲区的I/O操作转移到了操作系统 I/O 以流的方式处理数据,而 NIO 以缓冲区的方式处理数据:I ...

  2. 01_Hive简介及其工作机制

    1.Hive简介 Hive是一个基于Hadoop的一个数据仓库工具,可以将结构化的数据文件映射为一个表.并提供类SQL查询功能, 可以将sql语句转换为MapReduce任务运行.其优点是学习成本低, ...

  3. GVRP 的工作机制和工作模式

    GVRP 简介 GVRP 基于 GARP 的工作机制来维护设备中的 VLAN 动态注册信息,并将该信息向其他设备传播:当设备启动了 GVRP 之后,就能够接收来自其他设备的 VLAN 注册信息,并动态 ...

  4. Nginx 反向代理工作原理简介与配置详解

    Nginx反向代理工作原理简介与配置详解   by:授客  QQ:1033553122   测试环境 CentOS 6.5-x86_64 nginx-1.10.0 下载地址:http://nginx. ...

  5. keepalived之 Keepalived 原理(定义、VRRP 协议、VRRP 工作机制)

    1.Keepalived 定义 Keepalived 是一个基于VRRP协议来实现的LVS服务高可用方案,可以利用其来避免单点故障.一个LVS服务会有2台服务器运行Keepalived,一台为主服务器 ...

  6. Android休眠唤醒机制简介(一)【转】

    本文转载自:http://blog.csdn.net/zhaoxiaoqiang10_/article/details/24408129 Android休眠唤醒机制简介(一) ************ ...

  7. Spring学习记录2——简单了解Spring容器工作机制

    简单的了解Spring容器内部工作机制 Spring的AbstractApplicationContext是ApplicationContext的抽象实现类,该抽象类的refresh()方法定义了Sp ...

  8. android 6.0 高通平台sensor 工作机制及流程(原创)

    最近工作上有碰到sensor的相关问题,正好分析下其流程作个笔记. 这个笔记分三个部分: sensor硬件和驱动的工作机制 sensor 上层app如何使用 从驱动到上层app这中间的流程是如何 Se ...

  9. gitlab工作流程简介

    gitlab工作流程简介 新建项目流程 创建/导入项目 可以选择导入github.bitbucket项目,也可以新建空白项目,还可以从SVN导入项目 建议选择private等级 初始化项目 1.本地克 ...

随机推荐

  1. javascript通过url向jsp页面传递中文参数乱码解决方法

    解决方法:在传递参数前将中文参数进行两次编码,jsp页面获取参数后对中文参数进行一次解码,中文参数就不会变为乱码了! 参考例子: <%@ page language="java&quo ...

  2. 外网无法连接Kafka集群(报错:NoBrokersAvailable)

    本地Consumer和Producer无法使用远程Kafka服务器的解决方法: 分别修改各台服务器Kafka配置文件server.properties, 在#listeners=PLAINTEXT:/ ...

  3. [Parcel] Running TypeScript with parcel-bundler

    TO get started with TypeScirpt quickly in your local computer is using parcel-bunlder: npm i -g parc ...

  4. 持续集成之Jenkins+Gitlab简介 [一]

    转载:http://blog.csdn.net/abcdocker/article/details/53840449 持续集成概念 持续集成Continuous Integration 持续交付Con ...

  5. 用unity3d切割图片

    原地址:http://www.cnblogs.com/leng-yuye/archive/2012/05/31/2528148.html 需求:把图片的像素中不为alpha的部分切出来保存成单个图片. ...

  6. /proc/meminfo详解 = /nmon analysis --MEM

    memtotal hightotal lowtotal swaptotal memfree highfree lowfree swapfree memshared cached active bigf ...

  7. 用尽洪荒之力整理的Mysql数据库32条军规(转)

    今天上午吐血整理了Oracle SQL性能优化的40条军规,其中很多规则也是适用于Mysql的,结果今晚发现这一篇文章——用尽洪荒之力整理的Mysql数据库32条军规,和我的竟有异曲同工之妙,当然不同 ...

  8. 把sqlserver查询结果复制到Excel出现数据记录遗漏

    问题:今天在sqlserver查询,总共有10000记录,把结果复制到Excel,发现少掉352条,用导出csv也是如此. 原因:经排查发现缺少的记录是因为商品名称字段包含英文双引号". 解 ...

  9. 【转载】HTTP和SOAP完全就是两个不同的协议

    http:是一个客户端和服务器端请求和应答的标准(TCP). http协议其目的是为了提供一种发布和接收htttp页面的方法 http协议的客户端与服务器的交互:由HTTP客户端发起一个请求,建立一个 ...

  10. CSS3怎样实现超出指定文本以省略号显示效果

    作者:zhanhailiang 日期:2014-10-24 不做前端非常久了,今天从重构师那里了解到CSS3已经能够实现非常多以往必须通过JS才干实现的效果,如渐变,阴影,自己主动截断文本展示省略号等 ...