更多与异步javascript的斗争

时间:2011-12-05 14:13:55

标签: javascript asynchronous

我的申请旨在:   1.填充一些数组(使用JSON文件)   2.在...之前处理数组数据   3. ...在已准备好的DIV中插入已处理的数组数据

目前,这是以程序方式构建的,但正如Pointy指出的那样(http://stackoverflow.com/questions/8377344/scope-of-javascript-array-differs-from-ie9-to-firefox-chrome / 8377401#8377401),试图通过一些异步编程这样做。我目前的目标是通过使其正确异步,使其在所有浏览器中都能正常工作。

尽管应用程序在IE9中运行良好,但它在FF和Chrome中失败了。在以下主要过程中,IE9填充并保留所有数组内容。 FF等人填充然后丢失它。

//globally declare some arrays (used throughout the application)
function buildTree(id) {
    $(document).ready(function() {
        $.getJSON(JSONfile, function(data) {
            $.each(data.person, function(i, xdata) {
                //populate arrays with relevant data
            }); //end of first $.each()
            //check 1
        }); //end of first getJSON
        //check 2
        $.getJSON(JSONfile, function(data) {
            //check 3
            $.each(data.person, function(i, xdata) {
                //populate arrays with relevant data, using arrays from first read
            }); //end of second $.each()
            //check 4
        }); //end of second getJSON
        //check 5
        //check 6
    }); //end of document.ready
}

阵列很好:检查1,3,4,6 数组为空:检查2,5

为了给我的痛苦增添困惑,我决定将数组转储到DIV中而不进行处理。我意外地在(= check5)中留下了警报。虽然它仍然显示数组为空,但是当下一行执行(将数组转储到DIV中)时,一切都很好。评论警报:没有了。

看到任何明显错误的东西?

3 个答案:

答案 0 :(得分:1)

你有几个选择。

  1. 在第一个success函数中执行第二次JSON Ajax调用。 (“检查1”)
  2. 使用jQuery's .when/.then进行叠加。
  3. 在服务器端做更多工作,避免一共做Ajaxy。
  4. 让它们同步(ew,不要)。

答案 1 :(得分:0)

代码中的问题是两个AJAX请求都是立即发送的,没有任何保证第一个请求会在第二个之前返回。

你可以通过

来解决这个问题
  1. 仅在第一个AJAX请求完成后才发送第二个AJAX请求

    $.getJSON(..., function(data1){
        $.getJSON(..., function(data2){
        });
    });
    
  2. 明确地允许任何一个请求出现

    //I don't know if there is a function to do this kind of sync
    // built-in jQuery already. In Dojo I'd use a DeferredList...
    
    var requests_to_go = 2;
    var args = [];
    
    function onHaveAllData(args){
        var data1 = args[0];
        var data2 = args[1];
        //populate second array
    }
    
    $.getJSON(..., function(data){
        requests_to_go -= 1;
        args[0] = data;
        if(request_to_go <= 0){ onHaveAllData(args); }
    });
    
    $.getJSON(..., function(data){
        requests_to_go -= 1;
        args[1] = data;
        if(request_to_go <= 0){ onHaveAllData(args); }
    });
    

答案 2 :(得分:0)

这是一个具有欺骗性的问题。是的,它确实有异步情况(需要纠正),但真正的问题是:为什么我在FF的警报声明中看不到任何内容?目前,我并不在意,因为即使FireFox没有在警报中显示任何内容,它也会将内容传递给下一个例程,这就是我们将处理下一个问题的地方。