需要帮助理解这个JavaScript变量的作用范围。

huangapple go评论147阅读模式
英文:

Need help understanding the scope of this javascript variable

问题

在JavaScript中,在VueJS单页应用程序内,我正在尝试创建一个方法,通过仅传递Google Maps Places Service的place_id和要返回的字段来减少冗余代码。

getPlaceDetails (place, fields) {
  this.$refs.mapRef.$mapPromise.then((map) => {
    var placesServices = new window.google.maps.places.PlacesService(map)
    placesServices.getDetails({ placeId: String(place.place_id), fields: fields }, (result, status) => {
      if (status === window.google.maps.places.PlacesServiceStatus.OK) {
        alert(JSON.stringify(result))
        return result
      }
    })
  })
}

我正在从另一个方法内调用上述方法:

var place = this.getPlaceDetails(place, ['name', 'geometry', 'place_id'])

它成功调用...并且alert显示所需的JSON...但place为null。我尝试过在第一个承诺之后使用以下方法:

var vm = this

并将结果分配给应用级变量...甚至在第一个承诺之后的.then内,像这样:

getPlaceDetails (place, fields) {
  this.$refs.mapRef.$mapPromise.then((map) => {
    var vm = this
    var placesServices = new window.google.maps.places.PlacesService(map)
    placesServices.getDetails({ placeId: String(place.place_id), fields: fields }, (result, status) => {
      if (status === window.google.maps.places.PlacesServiceStatus.OK) {
        alert(JSON.stringify(result))
        vm.tempPlace = result
      }
    })
  }).then(function () {
    return this.tempPlace
  })
}

如何使该方法返回结果对象?

英文:

In javascript, within a VueJS SPA, I'm trying to create a method that will allow me to reduce redundant code by passing the Google Maps Places Service only a place_id and the fields I would like returned.

getPlaceDetails (place, fields) {
  this.$refs.mapRef.$mapPromise.then((map) => {
    var placesServices = new window.google.maps.places.PlacesService(map)
    placesServices.getDetails({ placeId: String(place.place_id), fields: fields }, (result, status) => {
      if (status === window.google.maps.places.PlacesServiceStatus.OK) {
        alert(JSON.stringify(result))
        return result
      }
    })
  })
}

I'm calling the above method from within another method:

var place = this.getPlaceDetails(place, ['name', 'geometry', 'place_id'])

It is invoked successfully... and the alert shows the desired JSON.. but place is null. I've tried using

var vm = this

above

var placesServices

and assigning the result to an app level variable... even inside of a .then after the first promise... like so:

getPlaceDetails (place, fields) {
  this.$refs.mapRef.$mapPromise.then((map) => {
    var vm = this
    var placesServices = new window.google.maps.places.PlacesService(map)
    placesServices.getDetails({ placeId: String(place.place_id), fields: fields }, (result, status) => {
      if (status === window.google.maps.places.PlacesServiceStatus.OK) {
        alert(JSON.stringify(result))
        vm.tempPlace = result
      }
    })
  }).then(function () {
    return this.tempPlace
  })
}

How can I get the method to return the result object??

答案1

得分: 0

代替return数据,您可以考虑将JSON赋值给Vue的观察数据变量,如下所示:

var somePlace = new Vue({
  el: '#someEl',
  data: {
    message: 'Hello robwolf.io',
    tempPlace: {} // <- 如果异步数据成功获取,这里将存储变量
  },
  methods: {
    getPlaceDetails (place, fields) {
      // [...您的Promise代码在这里...]
      }).then((result) => {
         this.tempPlace = JSON.stringify(result)
         // return this.tempPlace
      })
  // [....then函数也必须是箭头函数,以便访问tempPlace的作用域...]
})
英文:

Instead of returning the data, you may consider assigning the JSON to a Vue watched data variable, like so:

    var somePlace = new Vue({
      el: &#39;#someEl&#39;,
      data: {
        message: &#39;Hello robwolf.io&#39;,
        tempPlace: {} // &lt;- variable waiting for your asynchronous data if it comes thru
      },
      methods: {
      getPlaceDetails (place, fields) {
        // [...your promise code here...]
        }).then((result) =&gt; {
           this.tempPlace = JSON.stringify(result)
           // return this.tempPlace
        })
  // [...the .then function must also be an arrow function to have scope access to tempPlace...]

答案2

得分: 0

Promises

一个Promise(承诺)是一个将在将来的某个时刻解决(或拒绝)的对象。这对于执行需要不确定时间完成的异步任务(例如http调用)是必要的。

Promises可以进行_链式_操作,即一个接一个地执行。这就是.then方法的作用。使用.then,您传递一个函数,该函数将在Promise完成时立即执行。这个函数将接收到前一个Promise返回的对象。

你的方法

getPlaceDetails(place, fields) {
    return this.$refs.mapRef.$mapPromise.then((map) => {
        var vm = this;
        var placesServices = new window.google.maps.places.PlacesService(map);
        placesServices.getDetails({ placeId: String(place.place_id), fields: fields }, (result, status) => {
            if (status === window.google.maps.places.PlacesServiceStatus.OK) {
                alert(JSON.stringify(result));
                return result;
            }
        });
    });
}

这个方法将返回一个Promise,它将在将来的某个时刻产生所需的结果。

当您想要调用该方法时,您会得到这个Promise,并且必须处理它,再次通过传递一个函数(使用.then)来执行一旦结果准备好就会执行的函数。

this.getPlaceDetails(...).then((result) => {
    // 处理您的结果
})

或者,您可以使用await运算符来等待Promise完成:

var place = await this.getPlaceDetails(...);
英文:

Promises

A promise is an object that will resolve (or reject) in some point in the future. This is necessary to execute asynchronous tasks (e.g. http-calls) that take an undefined amount of time to finish.

Promises can be chained i.e. get executed one after another. This is what the .then method does. With .then you pass a function that will be executed as soon as the promise is finished. This function will receive the object that was returned by the previous promise.

Your method

getPlaceDetails (place, fields) {
    return this.$refs.mapRef.$mapPromise.then((map) =&gt; {
        var vm = this;
        var placesServices = new window.google.maps.places.PlacesService(map);
        placesServices.getDetails({ placeId: String(place.place_id), fields: fields }, (result, status) =&gt; {
            if (status === window.google.maps.places.PlacesServiceStatus.OK) {
                alert(JSON.stringify(result));
                return result;
            }
        });
    });
}

This Method will return a promise that - at some point in the future - will yield the desired result.

When you want to call the method you get that promise and have to handle it, again by passing a function (using .then) that will be executed once the result is ready.

this.getPlaceDetails(...).then((result) =&gt; {
    // handle your result
}}

Alternatively you could use the await operator to wait until the promise is finished:
var place = await this.getPlaceDetails(...);

huangapple
  • 本文由 发表于 2020年1月3日 15:31:19
  • 转载请务必保留本文链接:https://go.coder-hub.com/59574762.html
匿名

发表评论

匿名网友

:?: :razz: :sad: :evil: :!: :smile: :oops: :grin: :eek: :shock: :???: :cool: :lol: :mad: :twisted: :roll: :wink: :idea: :arrow: :neutral: :cry: :mrgreen:

确定