ES6 之异步流程的前世今生(上)
本文讲述了异步流程的演变过程。那么是什么是异步编程呢: 简单来讲就是执行一个指令不会马上返回结果而执行下一个任务,而是等到特定的事件触发后,才能得到结果。
基础知识
我们知道 javascript 运行在浏览器中,以 Google 浏览器为例子, v8 引擎,包含 内存堆: 这是内存分配发生的地方。 调用栈: 这是你代码执行的地方。
运行一个函数时,解析器把该函数添加到栈中并且执行这个函数。
Web APIs: DOM、AJAX、Timeout(setTimeout)
js是一门单线程的语言, 这意味这它只有一个调用栈。
当我们堆栈执行的函数需要大量时间时,浏览器会停止响应,幸运的是我们有异步回调。
javaScript引擎 运行在宿主环境中(浏览器或者 node),
CallbackQueue and Event Loop
事件循环和回调队列
调用栈和回调队列,当栈为空时,它会调取出队列中的第一个事件,放到调用栈中执行;
常见的 宏任务(macro-task)(这个队列也被叫做 task queue) 比如: setTimeout、setInterval、 setImmediate、script(整体代码)、 I/O 操作、UI 渲染等。
常见的 微任务(micro-task) 比如: process.nextTick、Promise、Object.observe、MutationObserver 等。常见的异步编程方案
回调函数
事件监听
发布/订阅
promise 对象
环境配置
一双能敲代码的手、一台能执行代码的电脑。 需要预先引入的库
callback()
第一阶段:回调函数
回调函数的弊端
代码书写顺序与执行顺序不一致,不利于维护
回调函数大多是匿名函数,bug 追踪困难
异步操作的代码变更,后期维护麻烦。
事件监听
采用了事件驱动模型,任务的执行不取决与代码的顺序,取决于某个事件是否发生。
发布/订阅
假定我们存在一个任务中心,当某个事件完成之后,我们就发射状态信号,调度中心可以通知订阅了该状态信号的其他任务。这个也称为观察者模式。
promise
第二阶段:Promise
定义阶段:promise(resolve, reject)分别成功或者失败时处理什么。
调用阶段:通过 then 函数实现,成功就执行 resolve,它会将 reslove 的值传递给最近的 then 函数,作为 then 函数的参数。如果出错 reject,那么交给 catch 来捕获异常
promise 的要点如下:
递归: 每个一步操作返回的都是 promise 对象
状态机: 三种状态 peomise 对象内部可以控制,不能在外部改变状态
全局异常处理
将回调函数中的结果延后到 then 函数里处理或交给全局异常处理
我们约定将每个函数的返回值都得是 promise 对象。 只要是 promise 对象, 就可以控制状态并支持 then 方法,将无限个 promise 对象链接在一起。
每个 promise 对象都有 then 方法, 也就是说 then 方法是定义在原型对象 promise.prototype 上的, 它的作用是为 promise 实例添加状态改变时的回调函数
一般情况下,只传 success 回调函数即可,fail 函数可选,使用 catch 来捕获函数异常比通过 fail 函数进行处理更加可控。
我们来看看下面这个例子:
new Promise 更为强大,Promise.resolve 更为便捷
以下是更为便捷的写法
promise 原理
上述代码就是一个简单的 promise 了,但是还有两点问题没有解决 1.链式调用 2.不传值时。 我们改造下
resolvePromsie 是什么呢: Promise A+ 2.27 规范
测试代码
增加 Promise.resolve、catch、race 方法
最后更新于
这有帮助吗?