Javascript 为什么承诺在循环中的工作方式不同?

Javascript 为什么承诺在循环中的工作方式不同?,javascript,promise,Javascript,Promise,我有delay函数生成器用于Promise。然后是方法 function delay(msec) { return (value) => { return new Promise((resolve, reject) => { setTimeout(() => { resolve(value); }, msec); }); } } 当我在没有循环的情况

我有
delay
函数生成器用于
Promise。然后是
方法

function delay(msec) {
    return (value) => {
        return new Promise((resolve, reject) => {
            setTimeout(() => {
                resolve(value);
            }, msec);
        });
    }
}
当我在没有循环的情况下使用
delay
函数时,它工作正常:

var promise = Promise.resolve();
promise
    .then(() => console.log(1))
    .then(delay(1000))
    .then(() => console.log(2))
    .then(delay(1000))
    .then(() => console.log(3))
    .then(delay(1000));
但当我在循环中使用它时,所有数字都会毫不延迟地打印出来:

var loopPromise = Promise.resolve();
for (let i = 1; i <= 3; i++) {
    loopPromise
        .then(() => console.log(i))
        .then(delay(1000));
}
var loopPromise=Promise.resolve();
for(设i=1;i console.log(i))
。然后(延迟(1000));
}
为什么承诺在循环中的工作方式不同?如何修复此循环行为

为什么承诺在循环中的工作方式不同

如果展开循环版本,您将执行以下操作:

var loopPromise = Promise.resolve();

loopPromise
    .then(() => console.log(1))
    .then(delay(1000));

loopPromise
    .then(() => console.log(2))
    .then(delay(1000));

loopPromise
    .then(() => console.log(3))
    .then(delay(1000));
即每个调用都直接进入
loopPromise
并立即被调用,而不是被链接

如何修复此循环行为

最简单的方法是通过覆盖原始的
Promise
变量来跟踪每次迭代中链的最新部分:

var loopPromise = Promise.resolve();
for (let i = 1; i <= 3; i++) {
    loopPromise = loopPromise
        .then(() => console.log(i))
        .then(delay(1000));
}
var loopPromise=Promise.resolve();
for(设i=1;i console.log(i))
。然后(延迟(1000));
}
为什么承诺在循环中的工作方式不同

如果展开循环版本,您将执行以下操作:

var loopPromise = Promise.resolve();

loopPromise
    .then(() => console.log(1))
    .then(delay(1000));

loopPromise
    .then(() => console.log(2))
    .then(delay(1000));

loopPromise
    .then(() => console.log(3))
    .then(delay(1000));
即每个调用都直接进入
loopPromise
并立即被调用,而不是被链接

如何修复此循环行为

最简单的方法是通过覆盖原始的
Promise
变量来跟踪每次迭代中链的最新部分:

var loopPromise = Promise.resolve();
for (let i = 1; i <= 3; i++) {
    loopPromise = loopPromise
        .then(() => console.log(i))
        .then(delay(1000));
}
var loopPromise=Promise.resolve();
for(设i=1;i console.log(i))
。然后(延迟(1000));
}
then结构大致模拟了常规的同步行为。循环继续,每个计时器独立触发,“then”基本上使触发同步。“then”构造大致模拟常规的同步行为。循环继续,每个计时器独立触发,而“then”基本上使触发同步。