Javascript 迭代数组,为每个元素调用$.ajax。返回包含所有ajax结果的数组

Javascript 迭代数组,为每个元素调用$.ajax。返回包含所有ajax结果的数组,javascript,ajax,jquery,Javascript,Ajax,Jquery,我刚刚开始使用JavaScript处理非琐碎的事情,所以这可能很简单 我试图完成的是:迭代一个产品引用数组,获取每个引用的JSON,并返回一个包含所有产品信息的数组(使用类似于散列的结构按引用索引) 我所尝试的: function fetchProductData(references){ var product_data = new Object(); references.forEach(function(ref){ $.ajax({ url: "http://l

我刚刚开始使用JavaScript处理非琐碎的事情,所以这可能很简单

我试图完成的是:迭代一个产品引用数组,获取每个引用的JSON,并返回一个包含所有产品信息的数组(使用类似于散列的结构按引用索引)

我所尝试的:

function fetchProductData(references){
  var product_data = new Object();
  references.forEach(function(ref){
    $.ajax({
      url: "http://localhost:3000/products/find.js?reference=" + ref,
      dataType: "jsonp",
      type: "GET",
      processData: false,
      contentType: "application/json",
      success: function(data) {
        product_data[ref] = data;
      }
    });
  });
  alert('before return: ' + product_data);
  return product_data;
};

$(document).ready(function(){
  var products = fetchProductData(references);
  alert('products : ' + products);
});
我不明白的是:第一次调用
alert
显示数组内容时,数组是空的。但是,在第二次调用中,数组中填充了我想要的数据

换句话说,“产品:
警报
显示了我想要在上面代码中显示的数据。但如果我对“返回前:
alert
”进行注释,它就不再这样做了。为什么会这样

所以我的问题是:我如何让jQuery进行几次$.ajax调用来获取产品信息,在一个数组中收集这些信息,然后返回那个数组,以便在代码中的其他地方使用它


另外,为什么变量中的数据在
警报中引用后可以神奇地访问?

您正在异步模式下执行ajax查询。你想要一个同步结果。尝试添加:

async: false

希望这会有所帮助。

您的
$。ajax
调用是异步的,因此发生的情况是,您第一次调用时,您的javascript会进行调用,然后转到下一行(警报),然后循环。您很抱歉,此时数据尚未返回。要解决这个问题,您可以在
$.ajax
调用中设置
async:false
选项。

在“ajax”中的“A”代表“asynchronous”:。您的程序不会等到调用完成后再进行下一次迭代,这意味着您可能无法获得所有数据。警报也有同样的问题。操作concat'before return:'到字符串添加足够的时间以获取变量中的一些数据。在速度更快的机器上,您可能会发现永远无法获取数据

我认为你真的需要重新考虑你的方法。在一个循环中有多个AJAX请求不是一个好主意。这将大大增加页面的延迟。使用JSON传递所有参数一次,然后让服务器端脚本循环通过该参数并返回JSON中的单个响应

function fetchProductData(references){
  // make sure your "references" is a JSON object
  $.getJSON('http://server/side/url', {'json':references}, function(product_data) {
      // do something with product_data (alert them, put them in an array, etc)

  });
}

这是一个异步操作。知道数据何时准备好的唯一可靠方法是回调函数:
success:function(){…}
,当数据最终返回时调用该函数。把你的警报放在那里

function fetchProductData(references, cb){
  var length = 0;
  var product_data = new Object();
  references.forEach(function(ref){
    length++;
    $.ajax({
      url: "http://localhost:3000/products/find.js?reference=" + ref,
      dataType: "jsonp",
      type: "GET",
      processData: false,
      contentType: "application/json",
      success: function(data) {
        product_data[ref] = data;
        if (++count === length) {
          cb(product_data);
        }
      }
    });
  });

};

$(document).ready(function(){
  var products = fetchProductData(references, function(products) {
    alert('products : ' + products);
  });
});
对异步操作使用回调


它之所以能够与
警报
调用一起工作,是因为警报消息给了ajax足够的时间来填充数组。只有在您单击警报框上的
OK
后,才会触发return语句,为您的代码提供一个250ms的窗口,用数据填充数组。

forEach
为ES5。它在IE8synchronous ajax中不起作用,因为列表将被阻塞,并且速度非常慢。您基本上必须等待
latency*references.length
。所以200个项目的清单是20秒。@Raynos,完全同意这不是一个很好的处理方法。理想情况下,最好使用一些批量方式来请求数据,或者部分批量加载,让用户处理这些数据,并让其他数据在后台处理(理想情况下,您永远不会使用同步XMLHTTPRequests:)。只需向服务器请求数据,并给出一些参数。并在服务器完成后处理数据。感谢您解释阵列填充延迟。我现在很清楚为什么会这样,如何这样。是的,我真的应该一次通过所有的推荐信。我不知道为什么我没有想到。。。谢谢