Android级连异步任务——Bolts-Android原理简介

简介: Parse开源了一个面向iOS和Android的底层库集合,统称为Bolts。根据Parse的公告,Bolts是Parse和Facebook共同努力将两家公司各自独立开发的小型底层工具类合并的结果。Bolts-Android为一个级联的异步任务。

Parse开源了一个面向iOS和Android的底层库集合,统称为Bolts。根据Parse的公告,Bolts是Parse和Facebook共同努力将两家公司各自独立开发的小型底层工具类合并的结果。Bolts-Android为一个级联的异步任务。

Bolts-Android github地址:
https://github.com/BoltsFramework/Bolts-Android

本文案例的 github地址:
https://github.com/xiaxveliang/Android_ThirdSource_Bolts

原理解析:

  • 级连异步任务,可按以下方式使用
Task.call(new Callable<Boolean>() {
    @Override
    public Boolean call() throws Exception {
        // 异步线程
        return true;
    }
}, Task.BACKGROUND_EXECUTOR).continueWith(new Continuation<Boolean, Object>() {
    @Override
    public Object then(Task<Boolean> task) throws Exception {
        // 异步线程
        return null;
    }
}, Task.BACKGROUND_EXECUTOR).continueWith(new Continuation<Object, Boolean>() {
    @Override
    public Boolean then(Task<Object> task) throws Exception {
        // UI线程
        return true;
    }
}, Task.UI_THREAD_EXECUTOR);
  • 可自定义线程池,来处理不同类型的任务

例如,我们除了有Task.BACKGROUND_EXECUTOR线程池,还可以有 NETWORK_EXECUTOR(只处理网络请求)、DISK_EXECUTOR(只处理Sdcard的读写)等线程池。

  • 可通过Task类waitForCompletion()方法,阻塞当前线程,直到Task任务运行结束
  • 每一个Task类的对象,均包含一个Continuation列表,用来管理当前Task对象全部的Continuation任务
    // 每一个Task对象都有一个自己的Continuation队列(continuations非全局,这样不同task的continuation就不会混淆)
    private List<Continuation<TResult, Void>> continuations = new ArrayList<>();
  • Continuation任务的执行时机

当前Task对象的call()方法运行结束后,会调用trySetResult()方法,将运行结果保存下来;并循环执行continuations列表中的任务。
Task.java类中trySetResult方法:

    //当前task,执行结束后的返回数据赋值
    //Sets the result on the Task if the Task hasn't already been completed.
    boolean trySetResult(TResult result) {
        synchronized (lock) {
            // 任务运行结束判断
            if (complete) {
                return false;
            }
            // 任务运行结束
            complete = true;
            // 任务结果赋值
            Task.this.result = result;
            // 唤醒lock wait等待(如果之前调用过waitForCompletion阻塞线程,那么此处会被唤醒)
            lock.notifyAll();
            // 循环执行continuations任务
            runContinuations();
            return true;
        }
    }

Task.java类中runContinuations方法:

//循环执行continuations任务
//问题: Continuation并没有区分执行线程呀?
//答:每一个Continuation又是一个封装的Continuation.then(),方法中将任务提交到的不同线程池
private void runContinuations() {
    synchronized (lock) {
        // 循环运行当前continuations列表任务
        for (Continuation<TResult, ?> continuation : continuations) {
            try {
               // 执行Continuation任务
                continuation.then(this);
           } catch (RuntimeException e) {
                throw e;
            } catch (Exception e) {
                throw new RuntimeException(e);
            }
       }
        // 当前Task的continuations队列置空
       continuations = null;
    }
}

问题:continuations如何将不同任务提交到不用的线程池呢???
答:每一个Continuation又是一个封装的Continuation.then(),方法中将任务提交到的不同线程池

Task.java类中continueWith方法:

public <TContinuationResult> Task<TContinuationResult> continueWith(
        final Continuation<TResult, TContinuationResult> continuation, final Executor executor,
        final CancellationToken ct) {

    // 上次task的完成情况
    boolean completed;
    // 构建一个新的task
    final TaskCompletionSource<TContinuationResult> tcs = new TaskCompletionSource<>();
    //
    synchronized (lock) {
        // 上次task的完成情况
        completed = this.isCompleted();
        // 如果上次task 未完成,添加到task列表
        if (!completed) {
            // 向continuations队列中添加一个“需提交到不同线程池执行的task任务”
            this.continuations.add(new Continuation<TResult, Void>() {
                @Override
                public Void then(Task<TResult> task) {
                    //
                    completeImmediately(tcs, continuation, task, executor, ct);
                    return null;
                }
            });
        }
    }
    // 上次任务完成,当前线程执行
    if (completed) {
        completeImmediately(tcs, continuation, this, executor, ct);
    }
    //
    return tcs.getTask();
}

这里可以看出每次提交的Continuation任务中,均封装了一个completeImmediately(tcs, continuation, task, executor, ct);来确定其运行的线程池等信息。

= THE END =

文章首发于公众号”CODING技术小馆“,如果文章对您有帮助,欢迎关注我的公众号。
文章首发于公众号”CODING技术小馆“,如果文章对您有帮助,欢迎关注我的公众号。
文章首发于公众号”CODING技术小馆“,如果文章对您有帮助,欢迎关注我的公众号。

目录
相关文章
|
2月前
|
安全 Android开发 Kotlin
Android经典实战之SurfaceView原理和实践
本文介绍了 `SurfaceView` 这一强大的 UI 组件,尤其适合高性能绘制任务,如视频播放和游戏。文章详细讲解了 `SurfaceView` 的原理、与 `Surface` 类的关系及其实现示例,并强调了使用时需注意的线程安全、生命周期管理和性能优化等问题。
164 8
|
1月前
|
Android开发
Android gradle task任务检查各个module之间资源文件冲突.md
Android gradle task任务检查各个module之间资源文件冲突.md
Android gradle task任务检查各个module之间资源文件冲突.md
|
28天前
|
缓存 Java 数据库
Android的ANR原理
【10月更文挑战第18天】了解 ANR 的原理对于开发高质量的 Android 应用至关重要。通过合理的设计和优化,可以有效避免 ANR 的发生,提升应用的性能和用户体验。
56 8
|
1月前
|
XML 前端开发 Android开发
Android View的绘制流程和原理详细解说
Android View的绘制流程和原理详细解说
39 3
|
2月前
|
ARouter 测试技术 API
Android经典面试题之组件化原理、优缺点、实现方法?
本文介绍了组件化在Android开发中的应用,详细阐述了其原理、优缺点及实现方式,包括模块化、接口编程、依赖注入、路由机制等内容,并提供了具体代码示例。
47 2
|
2月前
|
编解码 前端开发 Android开发
Android经典实战之TextureView原理和高级用法
本文介绍了 `TextureView` 的原理和特点,包括其硬件加速渲染的优势及与其他视图叠加使用的灵活性,并提供了视频播放和自定义绘制的示例代码。通过合理管理生命周期和资源,`TextureView` 可实现高效流畅的图形和视频渲染。
246 12
|
1月前
|
Android开发 Kotlin
Android面试题之Kotlin中如何实现串行和并行任务?
本文介绍了 Kotlin 中 `async` 和 `await` 在并发编程中的应用,包括并行与串行任务的处理方法。并通过示例代码展示了如何启动并收集异步任务的结果。
28 0
|
1月前
|
Java 调度 Android开发
Android面试题之Kotlin中async 和 await实现并发的原理和面试总结
本文首发于公众号“AntDream”,详细解析了Kotlin协程中`async`与`await`的原理及其非阻塞特性,并提供了相关面试题及答案。协程作为轻量级线程,由Kotlin运行时库管理,`async`用于启动协程并返回`Deferred`对象,`await`则用于等待该对象完成并获取结果。文章还探讨了协程与传统线程的区别,并展示了如何取消协程任务及正确释放资源。
27 0
|
Web App开发 API Android开发
|
6天前
|
开发框架 前端开发 Android开发
安卓与iOS开发中的跨平台策略
在移动应用开发的战场上,安卓和iOS两大阵营各据一方。随着技术的演进,跨平台开发框架成为开发者的新宠,旨在实现一次编码、多平台部署的梦想。本文将探讨跨平台开发的优势与挑战,并分享实用的开发技巧,帮助开发者在安卓和iOS的世界中游刃有余。
下一篇
无影云桌面