Javascript 承诺实现-为什么需要将处理程序存储为数组?

Javascript 承诺实现-为什么需要将处理程序存储为数组?,javascript,promise,Javascript,Promise,我在看《简单承诺》的实施情况 我这里有很多东西。。。但我不确定为什么这个特定的示例需要将处理程序存储为数组 如果我们只在以下代码挂起状态时推送数组 function handle(handler) { if (state === PENDING) { handlers.push(handler); } else { if (state === FULFILLED && typeof handler.onFulfilled === 'functi

我在看《简单承诺》的实施情况

我这里有很多东西。。。但我不确定为什么这个特定的示例需要将处理程序存储为数组

如果我们只在以下代码挂起状态时推送数组

function handle(handler) {
  if (state === PENDING) {
    handlers.push(handler);
  } else {
    if (state === FULFILLED &&
      typeof handler.onFulfilled === 'function') {
      handler.onFulfilled(value);
    }
    if (state === REJECTED &&
      typeof handler.onRejected === 'function') {
      handler.onRejected(value);
    }
  }
}
但是如果我们完成并改变状态=!在调用状态之前,由以下人员立即挂起

function fulfill(result) {
  state = FULFILLED;
  value = result;
  handlers.forEach(handle);
  handlers = null;
}

function reject(error) {
  state = REJECTED;
  value = error;
  handlers.forEach(handle);
  handlers = null;
}
即使done是异步调用的

this.done = function (onFulfilled, onRejected) {
  // ensure we are always asynchronous
  setTimeout(function () {
    handle({
      onFulfilled: onFulfilled,
      onRejected: onRejected
    });
  }, 0);
}
我看不出处理程序将有多个元素,因为无论何时处理,无论是否在其中处理另一个进程,我们都会观察新的promise对象

i、 e.在什么情况下,我们需要在同一承诺上存储多个成功与失败处理程序

我没看到

请帮助我理解。

承诺链确实不会在链的头部(第一个承诺)添加“附加处理程序”

在承诺链的情况下,链下的每个
。然后
catch
返回一个新的承诺,因此,对于承诺链,您只需要一个“处理程序”是正确的

然而,任何承诺都可能有不止一个“倾听者”。。。i、 你可以调用它的
。然后多次调用
方法。。。
.then
返回的承诺是新的,但是,
p
仍然是相同的承诺,因此对其调用的任何
。then
都作为处理程序添加

const p=newpromise((解析,拒绝)=>setTimeout(解析,2000,'result');
//这就是p上的处理程序[0]
p、 然后(r=>console.log(`promise-resolved with[${r}]`));
//这就是p上的处理程序[1]
p、 然后(r=>console.log(`您可以向一个承诺添加多个“侦听器”-这里的结果是[${r}]`));
//这是一个承诺链,它也只向承诺“p”添加一个处理程序
P
//这就是p上的句柄[2]
.then(r=>`第三个处理程序[${r}]`)//这将添加到处理程序中
.然后(console.log);//但这不是p上的处理程序,
//它是前一个“承诺”返回的承诺上的处理程序。然后“
承诺链确实不会向链的头部(第一个承诺)添加“其他处理程序”

在承诺链的情况下,链下的每个
。然后
catch
返回一个新的承诺,因此,对于承诺链,您只需要一个“处理程序”是正确的

然而,任何承诺都可能有不止一个“倾听者”。。。i、 你可以调用它的
。然后多次调用
方法。。。
.then
返回的承诺是新的,但是,
p
仍然是相同的承诺,因此对其调用的任何
。then
都作为处理程序添加

const p=newpromise((解析,拒绝)=>setTimeout(解析,2000,'result');
//这就是p上的处理程序[0]
p、 然后(r=>console.log(`promise-resolved with[${r}]`));
//这就是p上的处理程序[1]
p、 然后(r=>console.log(`您可以向一个承诺添加多个“侦听器”-这里的结果是[${r}]`));
//这是一个承诺链,它也只向承诺“p”添加一个处理程序
P
//这就是p上的句柄[2]
.then(r=>`第三个处理程序[${r}]`)//这将添加到处理程序中
.然后(console.log);//但这不是p上的处理程序,

//它是前一个`返回的承诺上的一个处理程序。然后`
您可以调用
。然后
在单个承诺上调用任意次数-每次这样做时,您都需要添加一个处理程序。顺便说一句,如果承诺挂起,您将永远不会真正实现对
处理程序这样的处理程序的调用。forEach(handle)e)。然后(e=>e)。。。诸如此类?事情是,每次我们用它来观察,它都会创造新的应许实例。我相信只有在这个特定的例子中,才能确保满足或拒绝。我能想象的另一件事是,当你调用done函数时,因为它是公开的,不会返回新的承诺。你可以调用
。然后对单个承诺调用
,次数可以根据你的喜好而定-每次这样做时,如果承诺被挂起,你需要添加一个处理程序,您永远不会真正实现对处理程序的调用,比如
handlers.forEach(handle)e)。然后(e=>e)。。。诸如此类?事情是,每次我们用它来观察,它都会创造新的应许实例。我相信只有在这个特定的例子中,才能确保满足或拒绝。我能想象的另一件事是当你调用done函数时,因为它是公开的,不会返回新的承诺。明白了。我想看看如何使处理程序具有多个元素。。。似乎在异步进程(或委托)上工作,而多个进程则在同一承诺对象上工作。甚至没有考虑过这个边缘案例。这是一个“边缘”案例吗?在我的本地测试场景中没有边缘案例的意思。我并没有真正考虑现实世界的应用程序。但现在我想到了实际场景,这就是异步编程的全部意义。明白了。我想看看如何使处理程序具有多个元素。。。似乎在异步进程(或委托)上工作,而多个进程则在同一承诺对象上工作。甚至没有考虑过这个边缘案例。这是一个“边缘”案例吗?在我的本地测试场景中没有边缘案例的意思。我并没有真正考虑现实世界的应用程序。但是现在我想到了实际场景,这就是异步编程的全部要点。