用函数依次处理数组中的每一项是一个常见的需求。
当需要同步的函数处理时通常会写出下面的代码:
var i = 0,length = arr.length;
for( ;i<length; i++){
asny(arr[i]);
}
//All array items has been processed!
当函数是异步的时候上面的方法就不能保证循环结束后所有的数组成员都已近处理完毕。如果数组成员需要一个一个的并行的处理一般需要下面的处理方法。
(function next(i,length,callback){
if(i<length){
asny(arr[i],function(value){
arr[i] = value;
next(i++,length,callnack)
});
}else{
callback();
}
})(0,arr.length,function(){
//all array items has been processed!
});
可以看到,以上代码在异步函数执行一次并返回执行结果后才传入下一个数组成员并开始下一轮执行,直到所有数组成员处理完毕后,通过回调的方式触发后续代码的执行。如果数组成员可以并行处理,但后续代码仍然需要所有数组成员处理完毕后才能执行的话,则异步代码会调整成以下形式:
(function(i,length,count,callback){
for(;i<length;i++){
(function(i){
asny(i,function(value){
arr[i] = value;
if(++count == length) callback();
})
})(i)
}
})(0,arr.length,0,function(){
//all array items has been processed!
})
可以看到,与异步串行遍历的版本相比,以上代码并行处理所有数组成员,并通过计数器变量来判断什么时候所有数组成员都处理完毕了。