首页 > 解决方案 > 在回调函数中访问数据

问题描述

我有一个用于对地址进行地理编码的功能,该地址返回相同地址的城市名称

  // geocode the given address
  geocodeAddress(address, callback) {
    this.mapsAPILoader.load().then(() => {
      var geocoder = new google.maps.Geocoder();
      geocoder.geocode({ 'address': address }, function (results, status) {
        if (status == google.maps.GeocoderStatus.OK) {
          results[0].address_components.forEach(arrAddress => {
            if (arrAddress.types[0] == "locality") {
              callback(arrAddress.long_name);
            }
          })
        } else {
          console.log("Geocode was not successful for the following reason: " + status);
        }
      });
    });
  };

当我调用该函数并想要打印城市名称时,它会从 geocodeAddress 函数下方的代码行打印“未定义”,然后正确打印城市名称

this.geocodeAddress(this.offerAddress, data => {
  this.hostCity = data;
  console.log(this.hostCity);
});
console.log(this.hostCity);

我试图在第二个 console.log 函数之前添加一些超时但没有任何成功

因此,我很感兴趣如何在从地理编码器返回数据后访问这个值,因为我需要使用这些数据存储在数据库中,如果我尝试像这样存储

    this.geocodeAddress(this.offerAddress, data => {
            this.hostCity = data;
            this.service.addData({"address": this.offerAddress, "city": this.hostCity}, "/data")
                .subscribe(data => {
                  this.router.navigate(['list']);
                })
          });

它存储数据但 router.navigate 无法正常工作

所以我需要在 geocodeAddress 回调函数之外访问 hostCity 的解决方案,或者如何在这个 geocodeAddress 回调函数中正确调用另一个函数

标签: javascriptangulargoogle-mapstypescriptgoogle-geocoder

解决方案


如果您使用的是 TypeScript,则可以让您的geocodeAddress方法返回 a Promise,而不是使用回调,然后使用async/await

async geocodeAddress(address): Promise<string[]> {
    return new Promise((resolve, reject) => {
        this.mapsAPILoader.load().then(() => {
           var geocoder = new google.maps.Geocoder();
           geocoder.geocode({ 'address': address }, function (results, status) {
               if (status == google.maps.GeocoderStatus.OK) {
                   const result: string[] = [];
                   results[0].address_components.forEach(arrAddress => {
                       if (arrAddress.types[0] == "locality") {
                           result.push(arrAddress.long_name);
                       }
                   });
                   resolve(results);
               } else {
                   console.log("Geocode was not successful for the following reason: " + status);
                   reject(status);
               }
           });
       });
    });
};

现在,此函数返回一个数组,其中包含您要查找的所有地址的长名称。要使用它:

const data: string[] = await this.geocodeAddress(this.offerAddress);
this.hostCity = data[0];
// do whatever you want now

通过这种方式,您可以获得异步编程的好处,同时具有同步编程的简单性。


推荐阅读