一、 乞丐版 promise
仅实现 非常乞丐版的 promise,仅有个形式
运作原理既是
then
方法负责收集thenCb
回调函数resolve
reject
则是负责处理收集过来的- 为了 保证 在
resolve
reject
处理回调队列前,回调队列收集完毕,在new Promise
时,加了一个延时,即exector
也并不是立即执行函数
1 | // the res is the value from resolve or reject |
二、 实现 promise 的 核心方法 then 的部分
then
方法返回一个全新的promise
- 由于 返回的是一个 全新的
promise
,这就导致了我们在进行如上例当中的链式调用的时候,thenCb
是被收集到不同的promise.callbacks
当中去了,也就不能使用 如上面的_flushQueue
方法 - 思路是
promiseA
中收集 下一个promiseB
的resolveB
方法 - 当
promiseA.resolveA(value)
后,promiseA.callbacks
队列执行,promiseA.callbacks
的this.value = callback(value)
执行, - 随后就是 调用
promiseB.resolve(this.value)
promiseB.resolve
的执行,又会 调用promiseB.callbacks
,即this.value = callback(this.value)
继而去执行promiseC.resolve(this.value)
- 从而又能实现
value
一直传递下去
- 由于 返回的是一个 全新的
Click More
1 | enum PromiseStatus { |
移除
setTimeout
- 当
promise
内部执行的代码为 异步时,then
方法可以实现 相应callbacks
收集 - 当
promise
内部执行的代码为 同步时,则在各个promise
resolve
后,直接运行then
中传入的回调,中间若没有异步行为,则全部同步的执行 - 这个时候就需要接入状态管理控制了
- 即在
resolve
之前promise
为Pendding
状态,这种情况下 不可以调用promise.callbacks
- 在
resolve
之后promise
为Fulfilled
orRejected
,这种情况下 则可以立即调用 相应promise.callbacks
- 即在
- 当
Click More
1 | enum PromiseStatus { |
三、 完善 resolve、reject 方法,处理 callback 返回值为 一个 promise 情况
当 callback
返回值 也是一个 promise
的时候,这个时候需要将 promise.resolve(value)
的 value
值传递给 promise
链条中去
情况:
PromiseA.then
的返回值是PromiseB
PromiseA.then(cb)
中的cb
的返回值为Promise0
- 现在的目的则是 将
Promise0.resolve(value)
的value
传递给PromiseB
具体执行流程:
PromiseA.resolve(valueA)
后,无论PromiseA
中是同步还是 异步,都会先执行PromiseA.then(callback)
当中的callback
- 也就是
return Promise0
- 随后 执行
PromiseB.resolve(Promise0)
以便 执行PromiseB.callbacks
PromiseB.resolve
执行时是需要 获取Promise0.resolve
的值,这个时候 就没有直接 执行PromiseB.callbacks
- 而是执行
Promise0.then(PromiseB)
这样Promise0.callbacks
就收集到了PromiseB.resolve
- 在
Promise0.resolve
之后,执行Promise0.callbacks
也就是执行PromiseB.resolve(value0)
- 这样 链条又重新链接起来,
PromiseB.resolve(value0)
后 执行相应的PromiseB.callbacks
1 | enum PromiseStatus { |
上例中具体的执行流程为:
new [promise-1]
new [promise-2]
,传入[promise-1]
与[promise-2]
内部的executor
均为异步[promise-1].then(callback1)
new [promise-3]
[promise-1].callbacks
收集{resolve: [promise-3].resolve, onFulfilledCb: callback1 }
callback1
为 一个promise
[promise-3].then(callback3)
new [promise-4]
[promise-3].callbacks
收集{resolve: [promise-4].resolve, onFulfilledCb: callback3}
callback3
为普通的同步执行的代码,无异步
- 链式调用的 各个
callback
是同步执行的,所以可以一下子收集完成 [promise-1]
异步代码执行完毕,主动调用[promise-1].resolve(async result)
[promise-1].state = fulfilled
[promise-1].value = async result
[promise-1].callbacks
循环调用- 获取
callback1
的值,即let valuePromise = callback1(async result)
注意,valuePromise
既是[promise-2]
- 值穿透,即 将
valuePromise
传递下去,也就是[promise-3].resolve(valuePromise)
- 获取
[promise-3].resolve([promise-2])
这时候就有点特殊了- 普通情况下,
resolve
的值为 一个基本类型的话,当前的promise.state
会 置为fulfilled
状态 [promise-3].resolve([promise-2])
时,[promise-3].state
仍为pendding
状态,也就没有 去执行[promise-3].callbacks
队列了[promise-3].resolve([promise-2])
时,执行的语句为[promise-2].then([promise-3].resolve)
,既是 将[promise-3].resolve)
作为[promise-2]
的callback
,即callback2 = [promise-3].resolve
new [promise-5]
[promise-2].callbacks
收集{resolve: [promise-5].resolve, onFulfilledCb: [promise-3].resolve)}
- 普通情况下,
[promise-2].resolve(async2 result)
[promise-2].state = fulfilled
[promise-2].value = async2 result
[promise-2].callbacks
循环调用- stepone: 获取
callback2
的值,即let value = [promise-3].resolve(async2 result)
- steptwo: 值穿透,即 将
value
传递下去,也就是[promise-5].resolve(value)
- stepone: 获取
- stepone:
[promise-3].resolve(async2 result)
过程[promsie-3].state = fulfilled
[promise-3].value = async2 result
,这样就拿到了[promise-2]
异步执行的结果!!![promise-3].callbacks
循环调用- 获取
callback3
的值,即let value = callback3(async result)
- 值穿透,即 将
value
传递下去,也就是[promise-4].resolve(value)
- 获取
[promise-4].resolve(value)
[promise-4].state = fulfilled
[promise-4].value = value
[promise-4].callbacks
队列为空,停止运行
- steptwo:
[promise-5].resolve(value)
[promise-5].state = fulfilled
[promise-5].value = value
[promise-5].callbacks
队列为空,停止运行
四、 参考资料的代码
Click More
1 | let promiseCount = 1; |