我的代码如下:
function test(obj) {
if(//some conditon) {
obj.onload();
}else{
obj.onerror();
}
}
for(var i=0;i<4;i++){
test({
onload:function(e){
//some code to run
},
onerror:function(e){
break;
}
});
}
要点是test()函数是一个发出XHR请求的函数(它实际上是Appcelerator Titanium平台的API,所以我无法控制它)而且我正在循环调用测试函数。我需要打破onerror函数的循环,但是我得到一个错误,说中断不在循环或switch语句中。我怎么能改写这个?
答案 0 :(得分:11)
如果您的代码示例确实代表了一些实际代码(即所有处理都在同一事件循环中完成),您可以执行以下操作:
function test(obj) {
if (some_condition) {
return obj.onload();
} else {
return obj.onerror();
}
}
var result;
for(var i=0; i<4; i++){
result = test({
onload:function(e){
//some code to run
return true;
},
onerror:function(e){
return false;
}
});
if (!result) {
break;
}
}
否则,如果异步完成,则必须按顺序调用test
,而不是并行调用。例如,
function test(obj) {
doSomeAjaxRequest(arguments, function (err, result) {
if (some_condition) {
obj.onload();
} else {
obj.onerror();
}
});
}
var f = function (i) {
if (i >= 4) return;
test({
onload:function(e){
//some code to run
f(i+1);
},
onerror:function(e){
break;
}
});
}
f(0);
答案 1 :(得分:3)
不可能。 for循环是同步过程,而Ajax请求则不是。这意味着当发生onerror回调时,for循环已经完成正在执行。
作为替代方案,您可以在onsuccess处理程序中引入一个检查,确认没有发生错误。
var errorOccured = false;
for(var i=0;i<4;i++){
test({
onload:function(e){
if(errorOccured) return;
//some code to run
},
onerror:function(e){
errorOccured = true;
}
});
}
答案 2 :(得分:3)
有点hacky,但是可以用处理程序函数做这样的事情。
var handler = function(array, callback){
for(var i=0, l=array.length, e=array[i]; i<l; ++i){
if(true === handler.exit){
handler.exit = false; //restore
return;
}
callback.call(null, e);
}
};
handler.exit = false;
handler([1,2,3], function(e){
console.log(e);
if(2 === e){
arguments.callee.caller.exit = true; // :-)
}
});
没有测试过这个,但也许你可以将函数绑定到调用范围甚至吗?
var handler = function(a, f){
this.exit = false;
for(var i=0, l=a.length, e=a[i]; i<l; ++i){
if(true === this.exit){
this.exit = false; //restore
return;
}
callback.call(this, e);
}
};
handler([1,2,3], function(e){
console.log(e);
if(2 === e){
this.exit = true;
}
});
答案 3 :(得分:0)
你不能破坏test()函数内部的循环。我认为在这种情况下最好的解决方案是在test()函数中抛出异常,然后在循环中捕获它并中断。
答案 4 :(得分:0)
也许你可以制作&#39; onload&#39;回调递归?
意思是,您只需拨打&#39;测试&#39; &#39; onload&#39;内的方法处理程序,这也意味着你按顺序发出所有请求,而不是同时发送所有请求。
答案 5 :(得分:0)
我接受了penartur的回答,但我修改了没有“休息”:
function test(obj) {
doSomeAjaxRequest(arguments, function (err, result) {
if (some_condition) {
obj.onload();
} else {
obj.onerror();
}
});
}
var f = function (i) {
if (i >= 4) return;
test({
onload:function(e){
//some code to run
f(i+1);
},
onerror:function(e){
console.log('stop');
}
});
}
f(0);