Jquery 等待ajax成功结束,然后再进行下一次迭代
我有一个for循环,循环遍历一个关联数组。对于每个条目,我必须发出一个ajax请求,并用检索到的数据填充另一个数组。Jquery 等待ajax成功结束,然后再进行下一次迭代,jquery,ajax,asynchronous,Jquery,Ajax,Asynchronous,我有一个for循环,循环遍历一个关联数组。对于每个条目,我必须发出一个ajax请求,并用检索到的数据填充另一个数组。 问题是成功回调是异步的,因此它只在循环被迭代后运行。这意味着我的数据数组中填充了上一个ajax请求结果的多个副本。 这是我的代码(简化): var通道={ “错误”:“频道错误”, “计划”:“渠道计划” }; var数据//初始数据为空 函数getData(){ 数据=新数组(); 用于(通道中的var系列数据){ var currentData=新数组(); $.ajax({
问题是成功回调是异步的,因此它只在循环被迭代后运行。这意味着我的数据数组中填充了上一个ajax请求结果的多个副本。 这是我的代码(简化):
var通道={
“错误”:“频道错误”,
“计划”:“渠道计划”
};
var数据//初始数据为空
函数getData(){
数据=新数组();
用于(通道中的var系列数据){
var currentData=新数组();
$.ajax({
键入:“获取”,
url:'http://'+serverAddress+':'+serverPort+'/GetChannelBufferAsJsonp?channelName='+channels[seriesData]+'&callback=?',
数据类型:“json”,
async:false,
成功:函数(json){
var time=new Date().getTime()+3600000;
for(var i=0;i
所以数据有两个元素(正确),但它们都来自“plan_channel”(即我的数据源)。
我知道这是ajax请求的一个经典的、众所周知的“问题”(或特性),但我不知道如何摆脱它。你能告诉我如何等待成功回调结束,然后再进行下一次迭代吗?这是我能看到的重构代码的唯一方法(我不知道)。不过这有点毫无意义。在我看来,你的设置全错了,你不应该那样做。我所能看到的最好的方法是在一个ajax请求中将整个数组发送到ajax脚本,在php(或其他)中处理所有数组,然后以javascript中所需的格式将其吐出。否则你最好找一个更好的方法。例如,您可以使用ajax请求来调用success调用中的
getData()
函数,而不是使用For循环
// add a global var...
var inLoop;
function getData() {
data = new Array();
for (var seriesData in channels) {
inLoop = true; // set to true
var currentData = new Array();
$.ajax({
type: "GET",
url: 'http://' + serverAddress + ':' + serverPort + '/GetChannelBufferAsJsonp?channelName=' + channels[seriesData] + '&callback=?',
dataType: "json",
async: false,
success: function (json) {
// set inLoop to false to get out of loop below
inLoop = false;
var time = new Date().getTime() + 3600000;
for (var i = 0; i < json.length; i++) {
currentData.push({
x: time + i * 30000,
y: json[i]
});
}
data.push({
id: seriesData,
name: "Production " + seriesData,
data: currentData
});
}, error: function () {
console.log("error", this);
}
});
// loop round this bit for a while
while(inLoop){
// wait
}
}
}
为了做到这一点,您可能需要计算通过函数或其他东西的次数,以便能够再次将下一个通道传递到函数。对于同步AJAX调用,您不能使用成功处理程序,必须在调用完成后返回结果 尝试使用Amplify.js(http://amplifyjs.com/)asyc设置为false时;它比jqueryajax函数更易于使用和整洁。别被额外的图书馆耽搁了 更新#1 你必须这么做
function getData() {
data = new Array();
for (var seriesData in channels) {
var currentData = new Array();
amplify.request.define( "ajaxExample1", "ajax", {
url: 'http://' + serverAddress + ':' + serverPort + '/GetChannelBufferAsJsonp?channelName=' + channels[seriesData] + '&callback=?',
dataType: "json",
async: false,
type: "GET"
});
// later in code
amplify.request( "ajaxExample1", function( json ) {
var time = new Date().getTime() + 3600000;
for (var i = 0; i < json.length; i++) {
currentData.push({
x: time + i * 30000,
y: json[i]
});
}
data.push({
id: seriesData,
name: "Production " + seriesData,
data: currentData
});
});
}
}
函数getData(){
数据=新数组();
用于(通道中的var系列数据){
var currentData=新数组();
amplify.request.define(“ajaxExample1”、“ajax”{
url:'http://'+serverAddress+':'+serverPort+'/GetChannelBufferAsJsonp?channelName='+channels[seriesData]+'&callback=?',
数据类型:“json”,
async:false,
键入:“获取”
});
//以后的代码
请求(“ajaxExample1”,函数(json){
var time=new Date().getTime()+3600000;
for(var i=0;igetData发送新请求代码>来自ajax请求的success函数,而不是使用for循环。因此,如果使用.getData(),您有一个success函数,当ajax请求完成并“成功”时会调用该函数?您的编辑打开了我的心扉,谢谢。我还不错,这是一个很好的解决方案,也可以推广!
var channels = {
"first" : "hello world",
"second" : "goodbye world"
}
function getData(channel){
$.ajax({
url: 'http://whatever.com/channel='+channel,
success: function(){
getData(nextchannel);
}
});
}
function getData() {
data = new Array();
for (var seriesData in channels) {
var currentData = new Array();
amplify.request.define( "ajaxExample1", "ajax", {
url: 'http://' + serverAddress + ':' + serverPort + '/GetChannelBufferAsJsonp?channelName=' + channels[seriesData] + '&callback=?',
dataType: "json",
async: false,
type: "GET"
});
// later in code
amplify.request( "ajaxExample1", function( json ) {
var time = new Date().getTime() + 3600000;
for (var i = 0; i < json.length; i++) {
currentData.push({
x: time + i * 30000,
y: json[i]
});
}
data.push({
id: seriesData,
name: "Production " + seriesData,
data: currentData
});
});
}
}