Android开发经验谈程序员技术干货

详解 kotlin 对 coroutines (2) 前传

2018-12-24  本文已影响18人  zidea

排队等公交,排队买票在我们人口众多的中国是常见的场景,现在我们有了手机,在等待时间我们可以学习、工作和娱乐。我们只有等到车,买完票才能上车。我们今天来看一看如何实现异步编程。

下面通过一个简单示例来解释异步编程的各种解决方案,以及最总我们为什么会选择 coroutines 而不是其他的解决方案呢。

我们先请求 token ,网络会返回一个 token 给我们。拿到 token 我就可以通过传递 item 来获取一个 post。

然后将获取的 post 的内容显示呈现给用户。

我们做这个事情一共分 3 步,分别是第 1 步拿 token ,2 获取 post ,3 显示 post,这 3 步是有一定顺序的,每一步都会依赖于上一步的结果,而且 1 和 2 都是异步的,是否能成功地获取结果是不确定,花费多长时间能够获取到结果也是不确定。以上就是我们故事设定好开始了。

当然我们可以通过线程来解决这个问题,这也是多年一直以来的解决方案。那么想象一下,如果让我们操控 1000 个线程,好完全没有问题,那么线程数增加到 100 00 ,也还可以。如果继续增加到 100 000 那么就超出我们的控制范围了。

我们基本是无法游刃有余地控制 100 000 条线程的。而且当达到一定数量即使再增加线程数,效率无法的得到显著提升。阿里巴巴对高并发的解决方案也是协程,可以看一下我的《双 11 背后的技术》中的分析。

回调是在 javascript 中处理异步的解决方案。以通过回调来解决异步问题。

在回调函数中来处理 requestTokenAsync 异步返回的 token。同样做法来处理 createPostAsync 中返回的 item。

好我们将上面代码用 callback 方式重构一下。下面就是重构后的代码。

其实正式的生产环境中的代码要比上面复杂的多,我们的 callback 会一层套一层,就像下面 code 这个形状,对于 developer 有些难于理解,虽然他的确解决异步的问题。

很多人将这个叫做 callback hell 也就做 callback 金字塔吧。除了难于理解,更糟糕的是这样做不好控制异常,异常无法反映真正的问题。

在 javascript 的新版本中,对异步编程给出全新的解决方案,提出 promises 对象的概念,我们可以通过 promise 获取返回数据,以及异步事件的描述,请求是成功还是失败,以及异常的描述。

Promise 是发生在未来对象,有了 promise 我们将 callback 中代码分离出独立出现,形式上看起来要清晰多了。不仅是形式上不同于 callback,内在机制也是略有不同的。这里 future promise 和 Rx 他们实现方式都是相同的,本质上没有什么区别。

我们用 promise 方式重新构建 createPostAsync 方法,方法会返回一个包裹了 Post 类型 Promise。通过 promise 我们获取这个异步方法(函数)在发起异步请求后的一切事情,请求是否成功呢,是否发生异常,发生了什么异常,如果成功了,返回的 post 数据,一切的一切都在 Promise 这个对象,通过 promise 来预知 createPostAsync 的未来。

Promise 可以组合使用,而且异常也还是可以扩散的。

但是,无法是 Future 也好,还是 Rx 也好,我们都需要花费精力来学习和研究提供众多的 cominator 。可能这一点还是不如 coroutines。 

上一篇 下一篇

猜你喜欢

热点阅读