Promise.all具有$ q Promise和JS事件循环

时间:2018-10-03 11:20:59

标签: javascript angularjs es6-promise angular-promise event-loop

假设我在空的AngularJS控制器中有以下代码:

Promise.all([Promise.resolve()]).then(() => console.log('Then'));
setTimeout(() => console.log('setTimeout callback')); 

我希望:

  1. Promise.all.then将被放入事件循环。
  2. setTimeout回调将被放入事件循环。

我们不会发出任何长时间的请求,因此应该有以下输出:
Then
setTimeout callback
而且有效。

但是如果我们将Promise.resolve()替换为$q.resolve()

Promise.all([$q.resolve()]).then(() => console.log('Then'));
setTimeout(() => console.log('setTimeout callback'));

输出将不同:
setTimeout callback
Then

这里是个小家伙:https://embed.plnkr.co/0h0i4CzuSgqMbYQtxZtU/
为什么输出不同? $q.resolve如何影响输出?

1 个答案:

答案 0 :(得分:0)

某些原因:

  • Promise.all不会“检测”已经履行的承诺,因此会立即返回立即解决的承诺。它总是使用其.then()方法等待输入承诺(无论如何,它也需要通过此方法吸收非本地承诺)。由于then回调始终是异步的,因此Promise.all(…)的结果始终是异步解决的(除非iterable为空),并且Promise.all(…).then(…)回调将在以后计划
  • 在事件循环中没有单个事件队列,但是对于不同的源有多个事件队列。因此,即使promise事情在事件循环中花了更多的“滴答声”,他们的队列也比在超时队列之前和之前更容易得到服务。
  • 我们不知道$q使用什么机制来使它的promise回调异步。我们只知道这不是本地承诺,因此使用了一个不同的,显然是“较慢”的队列。

通常,您不能(不应该)以任何特定顺序调用异步回调,除非他们的文档中提到了它。在需要时明确显示排序(例如,使用promise)。