2

这是我的一些代码:

for (var i = 0; i < recordList.length; i++) {
  var recordID = recordList[i];
  populateDataRow(i, recordID, columns) 
};
console.log("done");

populateDataRow是一个使用$.getJSON 问题的函数(至少在 Google Chrome 中),该语句在循环完成console.log之前很久就被触发了populateDataRow

4

2 回答 2

4

是的,console.log首先发生是因为getJSON异步的。您的代码会启动它,但它会在后续代码运行后稍后完成。

要处理这个问题,您需要在getJSON. 您上面的代码会记住它启动了多少次调用,并在继续之前等待那么多完成。

您还可以让您的populateDataRow函数返回 的返回值getJSON,保存这些对象,然后jQuery.when在它们全部完成时使用它来获取通知。

这是一个示例:Live Copy | 直播源

var deferreds = [],
    index;

for (index = 0; index < 4; ++index) {
  deferreds.push($.getJSON("http://jsbin.com/agidot/1", function() {
    display("One finished");
  }));
}
$.when.apply($, deferreds).then(function() {
  display("All finished")
});

function display(msg) {
  $("<p>").html(String(msg)).appendTo(document.body);
}

请注意,当所有四个调用都完成时,我们只会看到“全部完成”。

打电话$.when有点麻烦。出于某种原因,您不能只将一组Deferred对象传递给它。所以我曾经Function#apply调用它并将数组的每个条目作为离散参数传递。


我很惊讶$.when不接受数组并有效地处理它,但我在这里看到其他答案也说要使用applyHereHere

如果您要经常使用数组,我想我可能会在我的标准 jQuery 扩展工具包中使用它:

(function($) {
    $.whenAll = function(deferreds) {
        return $.when.apply($, deferreds);
    };
})(jQuery);

...然后上面的代码示例的结尾将是:

$.whenAll(deferreds).then(function() {
  display("All finished")
});
于 2013-05-09T16:39:01.160 回答
0

$.getJSON是 jQuery 的$.ajax()-function 的简写函数。XHR(或 AJAX)- 调用是异步的,您的其他代码将进一步执行,您需要提供一个回调函数,该函数在 AJAX 调用完成时执行。

从 API ( http://api.jquery.com/jQuery.getJSON/ )

$.getJSON('ajax/test.json', function(data) {

});

这里,function(data){}是回调函数,作为参数提供给getJSON. 如果你想对返回的数据做一些事情,你需要在这个函数中或者在这个函数执行之后做。

于 2013-05-09T16:41:46.860 回答