当前位置:   article > 正文

2024年Android最全使用 promise 重构 Android 异步代码_android 原生promise(1),Android开发社招面试总结_安卓promise

安卓promise

结尾

好了,今天的分享就到这里,如果你对在面试中遇到的问题,或者刚毕业及工作几年迷茫不知道该如何准备面试并突破现状提升自己,对于自己的未来还不够了解不知道给如何规划,可以来看看同行们都是如何突破现状,怎么学习的,来吸收他们的面试以及工作经验完善自己的之后的面试计划及职业规划。

这里放上一部分我工作以来以及参与过的大大小小的面试收集总结出来的一套进阶学习的视频及面试专题资料包,主要还是希望大家在如今大环境不好的情况下面试能够顺利一点,希望可以帮助到大家~

网上学习资料一大堆,但如果学到的知识不成体系,遇到问题时只是浅尝辄止,不再深入研究,那么很难做到真正的技术提升。

需要这份系统化学习资料的朋友,可以戳这里获取

一个人可以走的很快,但一群人才能走的更远!不论你是正从事IT行业的老鸟或是对IT行业感兴趣的新人,都欢迎加入我们的的圈子(技术交流、学习资源、职场吐槽、大厂内推、面试辅导),让我们一起学习成长!

reject函数:将Promise 对象状态从 pending 变成 rejected

then函数:回调 resolved状态的结果 catch函数:回调 rejected状态的结果

可以看到Promise的状态是非常简单且清晰的,这也让它在实现异步编程减少很多认知负担。

Why:为什么要考虑引入Promise

前面说的Promise 不就是 JavaScript 异步编程的一种思想吗,那这跟 Android 开发有什么关系? 虽然前端终端领域有所不同,但面临的问题其实是大同小异的,比如常见的异步回调导致回调地狱,逻辑处理不连贯等问题。 从事Android开发的同学应该对以下异步编程场景比较熟悉:

  • 单个网络请求
  • 多个网络请求竞速
  • 等待多个异步任务返回结果
  • 异步任务回调
  • 超时处理
  • 定时轮询

这里可以停顿思考一下,如果利用 Android常规的方式去实现以上场景,你会怎么做?你的脑子可能有以下解决方案:

  • 使用 Thread 创建
  • 使用 Thread + Looper + Handler
  • 使用 Android 原生 AsyncTask
  • 使用 HandlerThread
  • 使用 IntentService
  • 使用 线程池
  • 使用 RxJava 框架

以上方案都能在Android中实现异步任务处理,但或多或少存在一些问题和适用场景,我们详细剖析下各自的优缺点:

通过不同的异步实现方式的对比,可以发现每种实现方式都有适用场景,我们面对业务复杂度也是不一样的,每一种解决方案都是为了降低业务复杂度,用更低成本的方式来编码,但我们也知道代码写出来是给人看的,是需要持续迭代和维护,类似RxJava 这种框架于我们而言太复杂了,繁琐的操作符容易写出不易维护的代码,简单易理解应该是更好的追求,而不是炫技,所以我们才会探索用更轻量更简洁的编码方式来提升团队的代码一致性,就目前而言使用 Promise 来写代码将会有以下好处:

  • 解决回调地狱:Promise 可以把一层层嵌套的 callback 变成 .then().then()... ,从而使代码编写和阅读更直观
  • 易于处理错误:Promise 比 callback 在错误处理上更清晰直观
  • 非常容易编写多个异步操作的代码

How:怎么使用 Promise 重构业务代码?

这里由于我们的Java版本的Promise组件未开源,所以本部分只分析重构Case使用案例。

重构case1: 如何实现一个带超时的网络接口请求?

这是一段未重构前的获取付款码的异步代码:

可以看到以上代码存在以下问题:

  • 需要定义异步回调接口
  • 很多 if-else 判断,圈复杂度较高
  • 业务实现了一个超时类,为了不受网络库默认超时影响
  • 逻辑不够连贯,不易于维护

使用 Promise重构后:

可以看到有以下变化:

  • 消除了异步回调接口,链式调用让逻辑更连贯更清晰了
  • 通过 Promise 包装了网络请求调用,统一返回 Promise
  • 指定了 Promise 超时时间,无需额外实现繁琐的超时逻辑
  • 通过 validate 方法 替代 if - else 的判断,如果需要还可以定义校验规则
  • 统一处理异常错误,逻辑变得更加完备
重构case2:如何更优雅的实现长链接降级短链接?

重构前的做法:

代码存在以下问题:

  • 处理长链接请求超时,通过回调再处理降级逻辑
  • 使用Handler实现定时器轮询请求异步结果并处理回调
  • 处理各种逻辑判断,代码难以维护
  • 不易于模拟超时降级,代码可测试性差

使用Promise重构后:

第一个Promise处理长链接Push监听 ,设置5s超时,超时异常发生回调except方法,判断throwable 类型,如果为PromiseTimeoutException实例对象,则执行降级短链接。短链接是另外一个Promise,通过这种方式将逻辑都完全结果,代码不会割裂,逻辑更连贯。 短链接轮训查单逻辑使用Promise实现:

  • 最外层Promise,控制整体的超时,即不管轮询的结果如何,超过限定时间直接给定失败结果
  • Promise.delay(),这个比较细节,我们认定500ms轮询一定不会返回结果,则通过延迟的方式来减少一次轮询请求
  • Promise.retry(),真正重试的逻辑,限定了最多重试次数和延时逻辑,RetryStrategy定义的是重试的策略,延迟(delay)多少和满足怎样的条件(condition)才允许重试

这段代码把复杂的延时、条件判断、重试策略都通过Promise这个框架实现了,少了很多临时变量,代码量更少,逻辑更清晰。

重构case3:实现 iLink Push支付消息和短链接轮训查单竞速

后面针对降级策略重构成竞速模型,采用Promise.any很轻松得实现代码重构,代码如下图所示。

总结

本文提供一种异步编程的思路,借鉴了Promise思想来重构了Android的异步代码。通过Promise组件提供的多种并发模型能够更优雅的解决绝大部分的场景需求。

防踩坑指南

如果跟Activity或Fragment生命周期绑定,需要在生命周期结束时,取消掉promise的线程运行,否则可能会有内存泄露;这里可以采用AbortController来实现更优雅的中断 Promise。

并发模型

● 多任务并行请求

Promise.all():接受任意个Promise对象,并发执行异步任务。全部任务成功,有一个失败则视为整体失败。

Promise.allSettled(): 任务优先,所有任务必须执行完毕,永远不会进入失败状态。

Promise.any():接受任意个Promise对象,并发执行异步任务。等待其中一个成功即为成功,全部任务失败则进入错误状态,输出错误列表。

● 多任务竞速场景

Promise.race(): 接受任意个Promise对象,并发执行异步任务。时间是第一优先级,多个任务以最先返回的那个结果为准,此结果成功即为整体成功,失败则为整体失败。

扩展思考

  1. Promise 最佳实践

更多学习和讨论,欢迎加入我们!

有许多来自一线的技术大牛,也有在小厂或外包公司奋斗的码农,我们致力打造一个平等,高质量的Android交流圈子,不一定能短期就让每个人的技术突飞猛进,但从长远来说,眼光,格局,长远发展的方向才是最重要的。

这里有2000+小伙伴,让你的学习不寂寞~·

网上学习资料一大堆,但如果学到的知识不成体系,遇到问题时只是浅尝辄止,不再深入研究,那么很难做到真正的技术提升。

需要这份系统化学习资料的朋友,可以戳这里获取

一个人可以走的很快,但一群人才能走的更远!不论你是正从事IT行业的老鸟或是对IT行业感兴趣的新人,都欢迎加入我们的的圈子(技术交流、学习资源、职场吐槽、大厂内推、面试辅导),让我们一起学习成长!

习资料一大堆,但如果学到的知识不成体系,遇到问题时只是浅尝辄止,不再深入研究,那么很难做到真正的技术提升。**

需要这份系统化学习资料的朋友,可以戳这里获取

一个人可以走的很快,但一群人才能走的更远!不论你是正从事IT行业的老鸟或是对IT行业感兴趣的新人,都欢迎加入我们的的圈子(技术交流、学习资源、职场吐槽、大厂内推、面试辅导),让我们一起学习成长!

声明:本文内容由网友自发贡献,不代表【wpsshop博客】立场,版权归原作者所有,本站不承担相应法律责任。如您发现有侵权的内容,请联系我们。转载请注明出处:https://www.wpsshop.cn/w/空白诗007/article/detail/771065
推荐阅读
相关标签
  

闽ICP备14008679号