多个 xmlhttp 请求 - JSON 被覆盖

Multiple xmlhttp requests - JSON get's overwritten

我必须执行多个 xmlhttp 请求(每个国家一个)。问题是我的 JSON 总是被上次请求的结果覆盖。无论如何我可以解决这个问题吗?这是代码。

function getDataBetween()
{
    for (var i = 0; i < CountryNames.length; i++) 
    {
        var countryName = CountryNames[i];
        var xmlhttp = new XMLHttpRequest();

        xmlhttp.onreadystatechange=function()
        {
            if (xmlhttp.readyState==4 && xmlhttp.status==200) 
            {
                for (var a = 0; a < CountryNames.length; a++) 
                {
                    dataset[a] = JSON.parse(xmlhttp.responseText);
                    console.log(dataset[a]);
                }
            }
        }
        xmlhttp.open("GET","update.php?country=" + countryName + "&begin=" + beginTime + "&end=" + endTime + "&functionName=getActiveUsers", true);
        xmlhttp.send();
    }
    DrawStructure();
}

我已经在寻找 Promise 语法,但我不确定在这种情况下如何使用它,而且我尝试了多种方法,但我无法让它工作。 https://developer.mozilla.org/en-US/docs/Web/JavaScript/Reference/Global_Objects/Promise

您需要为每个请求跟踪单独的 xmlHttpRequest 对象。就像现在一样,您的 for 循环使用相同的变量来存储它们,因此它们后面的会覆盖后面的。有多种方法可以解决这个问题。一种方法是添加一个闭包,以便 for 循环的每次调用都有它自己的函数范围:

function getDataBetween()
{
    for (var i = 0; i < CountryNames.length; i++) 
    {
        (function() {
            var countryName = CountryNames[i];
            var xmlhttp = new XMLHttpRequest();

            xmlhttp.onreadystatechange=function()
            {
                if (xmlhttp.readyState==4 && xmlhttp.status==200) 
                {
                    for (var a = 0; a < CountryNames.length; a++) 
                    {
                        dataset[a] = JSON.parse(xmlhttp.responseText);
                        console.log(dataset[a]);
                    }
                }
            }
            xmlhttp.open("GET","update.php?country=" + countryName + "&begin=" + beginTime + "&end=" + endTime + "&functionName=getActiveUsers", true);
            xmlhttp.send();
        })();
    }
    DrawStructure();
}

您还可以将对 xmlhttp 的引用更改为对 this 的引用,这样您就不会在 onreadystatechange 处理程序中直接使用 xmlhttp 变量被覆盖:

function getDataBetween()
{
    for (var i = 0; i < CountryNames.length; i++) 
    {
        var countryName = CountryNames[i];
        var xmlhttp = new XMLHttpRequest();

        xmlhttp.onreadystatechange=function()
        {
            if (this.readyState==4 && this.status==200) 
            {
                for (var a = 0; a < CountryNames.length; a++) 
                {
                    dataset[a] = JSON.parse(this.responseText);
                    console.log(dataset[a]);
                }
            }
        }
        xmlhttp.open("GET","update.php?country=" + countryName + "&begin=" + beginTime + "&end=" + endTime + "&functionName=getActiveUsers", true);
        xmlhttp.send();
    }
    DrawStructure();
}