除了可以认为合适的同步AJAX调用之外,处理这样的事情的最佳方法是什么?
var A = getDataFromServerWithAJAXCall(whatever);
var B = getDataFromServerWithAJAXCallThatDependsOnPreviousData(A);
var C = getMoreDataFromServerWithAJAXCall(whatever2);
processAllDataAndShowResult(A,B,C);
如果我可以将回调传递给那些函数,我知道我可以使用闭包和lambdas来完成这样的工作:
var A,B,C;
getDataFromServerWithAJAXCall(whatever, function(AJAXResult) {
A= AJAXResult;
getDataFromServerWithAJAXCallThatDependsOnPreviousData(A, function(AJAXResult2) {
B= AJAXResult2;
processAllDataAndShowResult(A,B,C);
});
});
getMoreDataFromServerWithAJAXCall(whatever2, function(AJAXResult) {
C= AJAXResult;
processAllDataAndShowResult(A,B,C);
});
function processAllDataAndShowResult(A,B,C) {
if(A && B && C) {
//Do stuff
}
}
但它对我来说感觉不对或干净。那么有更好的方法或至少更简洁的方式来做同样的事情,还是只是因为我不习惯于javascript函数式编程?
顺便说一下,如果有帮助的话,我正在使用jQuery(1.4.2)。
谢谢。
答案 0 :(得分:5)
是的,jQuery的Deferred Object非常方便。
以下是$.when()
函数documentation中的示例,说明了问题的解决方案:
$.when($.ajax("/page1.php"), $.ajax("/page2.php")).done(function(a1, a2){
/* a1 and a2 are arguments resolved for the
page1 and page2 ajax requests, respectively */
var jqXHR = a1[2]; /* arguments are [ "success", statusText, jqXHR ] */
if ( /Whip It/.test(jqXHR.responseText) ) {
alert("First page has 'Whip It' somewhere.");
}
});
干杯!
答案 1 :(得分:0)
如果您可以使用jQuery 1.5,那么您应该可以使用deferred object和$.when()
$.when(getDataFromServerWithAJAXCall("Call 1"), getMoreDataFromServerWithAJAXCall("Call 2")).done(function(a1, a2) {
var jqXHR = a1[2];
jqXHR.responseText;
getDataFromServerWithAJAXCallThatDependsOnPreviousData(jqXHR.responseText);
});
简单地说,当前两个函数完成时,它将执行第三个函数。
<强> Example on jsfiddle 强>
答案 2 :(得分:0)
使每个AJAX调用的回调函数在一个常见的本地存储中检查/存储结果。并且具有从该容器读取的另一个处理函数,可以定期或由每个回调激活。这样,您可以保持功能清洁并专注于Ajax调用。这也使得累积可以轻松扩展到n个Ajax调用,并且在添加新调用时不必修改现有代码。
答案 3 :(得分:0)
使用所谓的'倒计时锁定'
countdownlatch
的变量
到达每个回调时倒计时(确保
同时倒计时异步错误。 countdownlatch==0
是否调用函数
processAllDataAndShowResult
使用这些异步同步的javascript的美妙之处在于实现倒计时非常容易,因为javascript是单线程的,即:由于竞争条件,因此countdownlatch
无法获得时髦的数字不存在(在这种情况下)。
修改强>
没有看到B依赖于A,但同样的原则适用:
var A,B,C;
var cdlatch = 2;
getDataFromServerWithAJAXCall(whatever, function(AJAXResult) {
A= AJAXResult;
getDataFromServerWithAJAXCallThatDependsOnPreviousData(A, function(AJAXResult2) {
B= AJAXResult2;
if(--cdlatch === 0){
processAllDataAndShowResult(A,B,C);
}
});
});
getMoreDataFromServerWithAJAXCall(whatever2, function(AJAXResult) {
C= AJAXResult;
if(--cdlatch === 0){
processAllDataAndShowResult(A,B,C);
}
});
function processAllDataAndShowResult(A,B,C) {
//Do stuff
}
我必须承认,这不像我之前描述的一般情况那样清楚,哦。