![](/img/trans.png)
[英]How to loop thorugh mongoDB with a promise and a forEach loop? I want to populate an Array
[英]How to use promise in forEach loop of array to populate an object
我在數組上運行 forEach 循環並進行兩次返回承諾的調用,我想填充一個對象 say this.options
,然后用它做其他事情。 現在,如果我使用以下代碼示例並首先進入 then 函數,我就會遇到異步問題。
$.when.apply($, someArray.map(function(item) {
return $.ajax({...}).then(function(data){...});
})).then(function() {
// all ajax calls done now
});
這是下面的工作代碼,但它僅適用於數組中的第一個元素,因為我在響應的.then
中調用結果函數。 我想先對數組的所有元素進行所有提取,然后調用結果函數來做某事。
array.forEach(function(element) {
return developer.getResources(element)
.then((data) = > {
name = data.items[0];
return developer.getResourceContent(element, file);
})
.then((response) = > {
fileContent = atob(response.content);
self.files.push({
fileName: fileName,
fileType: fileType,
content: fileContent
});
self.resultingFunction(self.files)
}).catch ((error) = > {
console.log('Error: ', error);
})
});
我如何在 forEach 循環完成后填充self.files
對象,然后使用 files 對象調用結果函數?
Promise.all()
在這里會有幫助:
var promises = [];
array.forEach(function(element) {
promises.push(
developer.getResources(element)
.then((data) = > {
name = data.items[0];
return developer.getResourceContent(element, file);
})
.then((response) = > {
fileContent = atob(response.content);
self.files.push({
fileName: fileName,
fileType: fileType,
content: fileContent
});
}).catch ((error) = > {
console.log('Error: ', error);
})
);
});
Promise.all(promises).then(() =>
self.resultingFunction(self.files)
);
這將為每個項目啟動 AJAX 調用,一旦調用完成,將每次調用的結果添加到self.files
,並在所有調用完成后調用self.resultingFunction()
。
編輯:根據 Yury Tarabanko 的建議進行簡化。
上面接受的解決方案的一個輕微變化是:
var promises = array.map(function(element) {
return developer.getResources(element)
.then((data) = > {
name = data.items[0];
return developer.getResourceContent(element, file);
})
.then((response) = > {
fileContent = atob(response.content);
self.files.push({
fileName: fileName,
fileType: fileType,
content: fileContent
});
}).catch ((error) = > {
console.log('Error: ', error);
})
});
Promise.all(promises).then(() =>
self.resultingFunction(self.files)
);
我使用Array.map
而不是Array.forEach
,這意味着我不需要先創建一個空數組,我只需重新使用現有的數組。
您可以查看類似問題的答案以獲得極好的提示。 那里給出的解決方案使用Array#reduce()
來避免在執行任何工作之前必須累積所有 Promises 而不是使用Promise.all()
。
下面的代碼是對使用Promise進行同步的簡單理解。
let numArr = [1,2,3,4,5];
let nums=[];
let promiseList = new Promise(function(resolve,reject){
setTimeout(()=>{
numArr.forEach((val)=>{
nums.push(val);
});
resolve(nums);
},5000)
})
Promise.all([promiseList]).then((arrList)=>{
arrList.forEach((array)=>{
console.log("Array return from promiseList object ",array);
})
});
上面的示例將保存數組nums 5 秒。 它會在發布后打印在控制台上。
您可以使用.map
作為一個循環,為數組的每個元素啟動 Promise 請求,並返回這些 Promise 的新 Array。 我也使用了解構,但不確定我們在這里是否需要它。
await Promise.all([...arr.map(i => "our promise func"())]);
聲明:本站的技術帖子網頁,遵循CC BY-SA 4.0協議,如果您需要轉載,請注明本站網址或者原文地址。任何問題請咨詢:yoyou2525@163.com.