2016-03-01 62 views
0

我正在从api加载数据,我需要在加载代码后运行一个函数。如何异步运行函数(XMLHttpRequest)

function make(query, callback){ 
    console.log("1"); 
    var results = makeRequest(query); 
    return callback(results); 
}; 

setPoints = function(results){ 
    console.log("2"); 
    for(var key in results) 
    { 
     console.log("3"); 
     var myLatLng = {lat: key.lat, lng: key.lon}; 
     var marker = new google.maps.Marker({ 
      position: myLatLng, 
      map: map, 
      title: 'Hello World!' 
     }); 
    } 
}; 

make(3, setPoints); 

makeRequest = function(place) { 
    var req = new XMLHttpRequest(); 
    req.open('GET', "https://trailapi-trailapi.p.mashape.com/?limit=25&q[city_cont]=San+Luis+Obispo&radius=205", true); 
    req.setRequestHeader('X-Mashape-Key', 'JwTKoEqkTbmsh3eqT0fBweCHYIAUp1h1GCbjsnkh59Bok0iqOC'); 
    req.onreadystatechange = function() { 
     if (req.readyState === 4) { 
      if (req.status >= 200 && req.status < 400) { 
       var response = JSON.parse(req.responseText); 
       var latLongs = response.places.map(function (key) { 
        return {lat: key.lat, lon: key.lon}; 
       }); 
       console.log("Returned"); 
       return latLongs; 
      } else { 
       alert("Failed to load " + req.status); 
       return null; 
      } 
     } 
    }; 
    req.send(); 
} 

我想代码记录“1,返回,2,3”。相反,它正在记录“1,2,返回”。

+0

我的意思是,你可以在['setTimeout'(https://developer.mozilla.org/en-US/docs/Web/API/WindowTimers/setTimeout)调用包裹。虽然你故意这样做,但似乎有点奇怪。 –

+3

您需要将该回调作为参数传递给'makeRequest'(这是实际的异步函数),您可以从'readystatechange'回调*调用它,而不是返回结果。 – Bergi

回答

2

解决方法是将回调传递给函数makeRequest。此回调在XMLHttpRequest完成后运行。

function make(query, callback){ 
    console.log("1"); 
    makeRequest(query,callback); 

}; 

setPoints = function(results){ 
    console.log("2"); 
    for(var key in results) 
    { 
     console.log("3"); 
     var myLatLng = {lat: key.lat, lng: key.lon}; 
     var marker = new google.maps.Marker({ 
      position: myLatLng, 
      map: map, 
      title: 'Hello World!' 
     }); 
    } 
}; 

make(3, setPoints); 
makeRequest = function(place, callback) { 
    var req = new XMLHttpRequest(); 
    req.open('GET', "https://trailapi-trailapi.p.mashape.com/?limit=25&q[city_cont]=San+Luis+Obispo&radius=205", true); 
    req.setRequestHeader('X-Mashape-Key', 'JwTKoEqkTbmsh3eqT0fBweCHYIAUp1h1GCbjsnkh59Bok0iqOC'); 
    req.onreadystatechange = function() { 
     if (req.readyState === 4) { 
      if (req.status >= 200 && req.status < 400) { 
       var response = JSON.parse(req.responseText); 
       var latLongs = response.places.map(function (key) { 
        return {lat: key.lat, lon: key.lon}; 
       }); 
       console.log("Returned"); 
       return callback(latLongs); 
      } else { 
       alert("Failed to load " + req.status); 
       return null; 
      } 
     } 
    }; 
    req.send(); 
} 

另一个可怕的解决方案在你的问题是做功能makeRequest同步。

在方法XMLHttpRequest.open中,您可以在第三个参数中定义AJAX a/synchronous函数(只应将值true更改为false)。

makeRequest = function(place) { 
    var req = new XMLHttpRequest(); 
    req.open('GET', "https://trailapi-trailapi.p.mashape.com/?limit=25&q[city_cont]=San+Luis+Obispo&radius=205", false); 
    req.setRequestHeader('X-Mashape-Key', 'JwTKoEqkTbmsh3eqT0fBweCHYIAUp1h1GCbjsnkh59Bok0iqOC'); 
    req.onreadystatechange = function() { 
     if (req.readyState === 4) { 
      if (req.status >= 200 && req.status < 400) { 
       var response = JSON.parse(req.responseText); 
       var latLongs = response.places.map(function (key) { 
        return {lat: key.lat, lon: key.lon}; 
       }); 
       console.log("Returned"); 
       return latLongs; 
      } else { 
       alert("Failed to load " + req.status); 
       return null; 
      } 
     } 
    }; 
    req.send(); 
} 
+0

一个简单而简单的可怕解决方案。 – Bergi

+0

是的,它是可怕的解决方案,但在他的问题中获得了预期的结果。你会解释回调之间的不同,并结束函数或同步函数。谢谢 :)。 – caballerog

+0

OP已经试图使用回调,他只错过了一步。这个解决方案是不恰当的。 – Bergi

相关问题