递归Promise.all?
Recursive Promise.all?
我正试图等待一堆承诺完成。我知道我可以用 Promise.all
来做到这一点,但我不知道当其中一个承诺将一个新承诺推入承诺列表时该怎么做。
示例:
asyncFunction(...).then(result => {
// do something
});
asyncFunction(...).then(result => {
for(let row of result) {
asyncFunction(row);
}
});
console.log(promises.length); // 2
await Promise.all(promises);
console.log(promises.length); // 5
其中 asyncFunction
类似于:
const asyncFunction = (...args) => {
let result = new Promise((resolve, reject) => {
pool.query(...args, (err, rows, fields) => {
if (err) {
reject(err);
} else {
resolve(rows);
}
});
});
promises.push(result);
return result;
};
这里发生的是对 asyncFunction
的前两次调用将承诺推送到我的 promises
数组中,因此 promises.length
是 2。但是,在等待它们完成之后,第二个在 Promise.all
已经评估了那个数组之后将一堆新的承诺推入数组,所以他们没有等待。
那么,我如何才能等待所有的承诺,以及任何新的承诺?在此示例中,只需调用 await Promise.all(promises)
两次即可,但这可能会无限期地继续下去。
您可以编写一个递归的 all 函数,在每次迭代后重新评估列表的状态:
function recursiveAll( array ) {
// Wait for the promises to resolve
return Promise.all( array ).then(function( result ) {
// If no new promises were added, return the result
if ( result.length == array.length )
return result;
// If new promises were added, re-evaluate the array.
return recursiveAll( array );
});
}
我认为简单地用这个替换 Promise.all
应该可以正常工作:
while(promises.length) {
await promises.shift();
}
这就是有副作用的函数的问题。
您的代码有点抽象,无法为您提供准确的答案,但我建议您完全放弃 promises
-Array。
const asyncFunction = (...args) => {
return new Promise((resolve, reject) => {
pool.query(...args, (err, rows, fields) => {
if (err) {
reject(err);
} else {
resolve(rows);
}
});
});
}
和
asyncFunction(...).then(result => Promise.all(result.map(row => asyncFunction(row))) );
据我了解您的意图,这应该会导致数组嵌套在数组中,在最坏的情况下,现在只需展平即可获得所有值,而那些值则由前一个触发一个。
我正试图等待一堆承诺完成。我知道我可以用 Promise.all
来做到这一点,但我不知道当其中一个承诺将一个新承诺推入承诺列表时该怎么做。
示例:
asyncFunction(...).then(result => {
// do something
});
asyncFunction(...).then(result => {
for(let row of result) {
asyncFunction(row);
}
});
console.log(promises.length); // 2
await Promise.all(promises);
console.log(promises.length); // 5
其中 asyncFunction
类似于:
const asyncFunction = (...args) => {
let result = new Promise((resolve, reject) => {
pool.query(...args, (err, rows, fields) => {
if (err) {
reject(err);
} else {
resolve(rows);
}
});
});
promises.push(result);
return result;
};
这里发生的是对 asyncFunction
的前两次调用将承诺推送到我的 promises
数组中,因此 promises.length
是 2。但是,在等待它们完成之后,第二个在 Promise.all
已经评估了那个数组之后将一堆新的承诺推入数组,所以他们没有等待。
那么,我如何才能等待所有的承诺,以及任何新的承诺?在此示例中,只需调用 await Promise.all(promises)
两次即可,但这可能会无限期地继续下去。
您可以编写一个递归的 all 函数,在每次迭代后重新评估列表的状态:
function recursiveAll( array ) {
// Wait for the promises to resolve
return Promise.all( array ).then(function( result ) {
// If no new promises were added, return the result
if ( result.length == array.length )
return result;
// If new promises were added, re-evaluate the array.
return recursiveAll( array );
});
}
我认为简单地用这个替换 Promise.all
应该可以正常工作:
while(promises.length) {
await promises.shift();
}
这就是有副作用的函数的问题。
您的代码有点抽象,无法为您提供准确的答案,但我建议您完全放弃 promises
-Array。
const asyncFunction = (...args) => {
return new Promise((resolve, reject) => {
pool.query(...args, (err, rows, fields) => {
if (err) {
reject(err);
} else {
resolve(rows);
}
});
});
}
和
asyncFunction(...).then(result => Promise.all(result.map(row => asyncFunction(row))) );
据我了解您的意图,这应该会导致数组嵌套在数组中,在最坏的情况下,现在只需展平即可获得所有值,而那些值则由前一个触发一个。