关于承诺的Javascript采访
这是我在采访中被问到的一个问题。我知道数组将只返回零,因为这是异步的,但为什么会发生这种情况,以及如何修复它以使结果数组插入适当的数据 问题:假设findData是一个接受查询对象并返回查询结果承诺的函数。还假设someRandomArrayOfQueries是一个查询对象数组。解释以下代码将打印什么以及为什么:关于承诺的Javascript采访,javascript,promise,Javascript,Promise,这是我在采访中被问到的一个问题。我知道数组将只返回零,因为这是异步的,但为什么会发生这种情况,以及如何修复它以使结果数组插入适当的数据 问题:假设findData是一个接受查询对象并返回查询结果承诺的函数。还假设someRandomArrayOfQueries是一个查询对象数组。解释以下代码将打印什么以及为什么: function runMultipleQueries(queries) { var results = []; queries.forEach(doQuery); retur
function runMultipleQueries(queries) {
var results = [];
queries.forEach(doQuery);
return results;
function doQuery(query) {
findData(query)
.then(results.push.bind(results));
}
}
function log(value) {
console.log(value);
}
runMultipleQueries(someRandomArrayOfQueries).forEach(log);
doQuery
将在将来的某个时间执行。但是,会立即返回并记录阵列。因此,阵列仍然为空,没有任何记录。
要修复此问题,runMultipleQueries还需要返回一个承诺。那可能看起来像这样
function runMultipleQueries(queries) {
return Promise.all(queries.map(findData));
}
function log(value) {
console.log(value);
}
runMultipleQueries(someRandomArrayOfQueries).then(function(results) {
results.forEach(log);
});
如果您想保持runMultipleQueries
与原来的类似,您也可以创建这样的新承诺,但这将是不必要的复杂
function runMultipleQueries(queries) {
return new Promise(function(resolve, reject) {
var results = [];
queries.forEach(doQuery);
function doQuery(query) {
findData(query)
.then(function(result) {
results.push(result);
if(results.length === queries.length) resolve(results);
}, reject);
}
});
}
您也可以将结果记录在doQuery
中,但是您无法保证记录结果的顺序。而且,在您记录这些结果之后,这将使您更难对这些结果执行任何其他操作
function runMultipleQueries(queries) {
queries.forEach(doQuery);
function log(value) {
console.log(value);
}
function doQuery(query) {
findData(query)
.then(log);
}
}
runMultipleQueries(someRandomArrayOfQueries);
你确定这是普通的JavaScript吗?你需要阅读异步过程JavaScript。重要的是,你不知道时间会是什么时候。承诺不会阻碍这个过程。承诺只是一种承诺,当他拥有数据时,他将在其中执行代码,或者在catch中执行错误。返回函数将在任何时候执行,因为javascript进程将继续执行代码行。@PaulS。代码看起来不错。我想我们假设在这种情况下findData(查询)需要很长时间,因为他们试图测试您对单线程javascript的了解。我是否可以通过在promise中添加控制台日志来修复它?你能做到吗?你能做到-我又加了一个例子。但我建议不要这样做。