如何在promise then方法中将元素推入数组

时间:2019-08-07 09:58:45

标签: node.js promise

我正在尝试将元素放置在已在方法外部定义的数组中。

let result = JSON.parse(body);
let objects = [];
result.results.forEach(element => {
    getObjectDetail(element.place_id).then((detail) => {
        console.log(detail);
        let object = {
            place_id: element.place_id,
            name: element.name,
            rating: element.rating,
            address: detail.result.formatted_address,
            photo:
                   googleApiHost +
                   googlePlacePrefix +
                   googlePlacesPlaceImageUri +
                   '?key=' +
                   googleApiKey +
                   '&maxwidth=400&photoreference=' +
                   element.photos[0].photo_reference,
                   website: detail.result.website
         }
         console.log(object);
         objects.push(object);
     });
});
console.log(objects);

console.log(object)在设置了所有字段的情况下都给我带来了良好的效果。 但是console.log(objects)返回一个空数组

2 个答案:

答案 0 :(得分:1)

这是promise的全部概念-它异步运行并在解析后执行.then子句。但是与此同时,主代码流继续执行。

有效地,这意味着在您的情况下,流程如下所示: 进入forEach循环>为每个元素初始化一个单独的Promise> log(objects)>为每个已解决的Promise执行.then子句。

因此,在解决任何承诺并将任何项目推送到对象之前,将执行日志记录。 在这里最好的选择是使用Promise.all,它可以处理多个诺言,并在所有个诺言得到解决时返回已解决的诺言,或者在一个诺言时被拒绝的诺言承诺被拒绝。

let result = JSON.parse(body);
let objects = [];
let objectsPromises = [];
result.results.forEach( (element, index) => {
    objectsPromises[index] = getObjectDetail(element.place_id);
});
Promise.all(objectsPromises).then( (values) => {
   // The "values" is an array containing all the values of the resolved promises.
   // You can now iterate over it and perform the code in your `.then` clause for each 
   //promise, and then manipulate the objects array, as this iteration is synchronous 
   // (operates on actual values and not promises)
}
console.log(objects); // NOTE: THIS WILL STILL LOG EMPTY ARRAY!

答案 1 :(得分:0)

与for每个循环相比,您可以更好地使用for循环,因为forEach循环包含一个回调,并尝试使用async等待,它使代码更具可读性。

const func = async ()=> { 
    let result = JSON.parse(body);
    let objects = [];
    for (var element of result.results) {
    var detail = await getObjectDetail(element.place_id);
        console.log(detail);
        let object = {
            place_id: element.place_id,
            name: element.name,
            rating: element.rating,
            address: detail.result.formatted_address,
            photo: googleApiHost +
                    googlePlacePrefix +
                    googlePlacesPlaceImageUri +
                    '?key=' +
                    googleApiKey +
                    '&maxwidth=400&photoreference=' +
                    element.photos[0].photo_reference,
                    website: detail.result.website
            }
        console.log(object);
        objects.push(object);
    }
}

console.log(objects);