我正在将UnderscoreJs与nodejs一起使用,并且需要_.times()
方法。 times()将调用一个函数X次
这可以按预期工作,但是我需要进行一系列的迭代,而不是并行进行迭代。
知道是否可以使用带有回调方法的系列方法吗?
最佳答案
给定这样的东西:
function f() {
some_async_call({ callback: function(err, results) {...})
}
_(3).times(f);
然后,三个
f
调用将串行发生,但some_async_call
调用不一定是串行发生的,因为它们是异步的。如果要强制您的调用按顺序运行,则需要使用异步调用上的回调来启动该系列中的下一个:
function f(times, step) {
step = step || 0;
some_async_call({
callback: function(err, results) {
// Do something with `err` and `results`...
if(step < times)
f(times, step + 1);
}
});
}
f(3);
该方法将依次执行三个
some_async_calls
,但是,很遗憾,初始f(3)
将立即返回。当然,解决该问题的一种方法是另一种回调:function f(from_n, upto, and_finally) {
some_async_call({
callback: function(err, results) {
// Do something with `err` and `results`...
if(from_n < upto)
f(from_n + 1, upto, and_finally);
else
and_finally();
}
});
}
f(0, 3, function() { console.log('all done') });
_.times
放在哪里?真的没有。 _.times
is just a for
loop:_.times = function(n, iterator, context) {
for (var i = 0; i < n; i++) iterator.call(context, i);
};
_.times
存在是为了完整性,并允许您在使用for
时添加_.chain
循环。如果您确实愿意,可以穿上它,但是这样做只会使您一团糟,而不是简化代码。您可以使用250R的异步思想,但必须构建三个函数的数组,但是
_.range
和_.map
比_.times
更适合此功能:// Untested off the top of my head code...
function f(callback) {
some_async_call({
callback: function(err, results) {
// Deal with `err` and `results`...
callback();
}
});
}
var three_fs = _(3).range().map(function() { return f });
async.series(three_fs);
但是您仍然必须修改
f
以具有回调函数,并且如果您始终总是调用f
3次,则:async.series([f, f, f]);
可能比使用
_.range
和_.map
动态构建阵列更好。真正的教训是,一旦您进入异步函数调用,您最终将所有逻辑实现为回调,回调,回调,回调。