通过javascript中的事件控制流程代码

时间:2015-06-02 04:17:28

标签: javascript control-flow

[1,2,3].map(function(num) {
  client.fooBar(num);
  // don't move on until `foo` is emitted to `client`
});

client.on('foo', function(num) {
   console.log(num)
});

调用client.fooBar时,将进行异步调用,并在foo上发出事件client。如果我只想一次处理一个号码(在2处理之前不要移动到1),那么组织我的代码的最佳方法是什么?这是node.js。

1 个答案:

答案 0 :(得分:1)

  

没有。这是一个完全不同的问题(switz)。

不,它完全不同。你有一系列需要围绕它的异步(事件驱动)控制结构。

因为您的fooBar函数触发foo事件而不是回调,您需要将foo事件侦听器附加到控件代码以通知循环何时继续数组中的下一个元素。

除非有其他方法让控制结构知道何时继续,否则我看不到另一种完成任务的方法。

这使用async.eachSeries来实现您的目标

async.eachSeries([1,2,3], function(num, done) {
  client.once("foo", function() { done(); });
  client.fooBar(num);
}, function(err) {
  if (err) throw err;
  console.log("all done!");
});

如果您不想依赖async lib,您可以编写自己的asyncForEach函数

function asyncForEach(arr, iterator, callback) {
  var queue = arr.slice(0);
  function next(err) {
    if (err) return callback(err);
    if (queue.length === 0) return callback(null);
    iterator(queue.shift(), next);
  }
  next();
}

然后在您的代码中使用它

asyncForEach([1,2,3], function(num, done) {
  client.once("foo", function() { done(); });
  client.fooBar(num);
}, function(err) {
  if (err) throw err;
  console.log("all done!");
});