Java语言如何在for循环完成后执行代码 [英] Javascript how to execute code after for loop completes

查看:193
本文介绍了Java语言如何在for循环完成后执行代码的处理方法,对大家解决问题具有一定的参考价值,需要的朋友们下面随着小编来一起学习吧!

问题描述

我正在尝试解决这种js/async情况,并且试图了解其他JS世界如何处理此问题.

I'm trying to work through this js/async scenario and i'm trying to know how the rest of the js world handles this.

function doStuff(callback) {

  cursor.each(function(err, blahblah) {
    ...doing stuff here takes some time
  });

  ... Execute this code ONLY after the `cursor.each` loop is finished
  callback();

编辑

这是一个更具体的示例,使用下面的大多数建议进行了更新,但这些建议仍然无效.

Here's a more concrete example updated using most of the suggestions below which still doesn't work.

function doStuff(callback) {

  MongoClient.connect(constants.mongoUrl, function(err, db) {

    var collection = db.collection('cases2');
    var cursor = collection.find();

    var promises = [];  // array for storing promises

    cursor.each(function(err, item) {

      console.log('inside each'); // NEVER GETS LOGGED UNLESS I COMMENT OUT THIS LINE: return Q.all(promises).then(callback(null, items));

      var def = Q.defer();        // Create deferred object and store
      promises.push(def.promise); // Its promise in the array

      if(item == null) {
        return def.resolve();
      }

      def.resolve();  // resolve the promise
    });

    console.log('items'); // ALWAYS GETS CALLED
    console.log(items);

    // IF I COMMENT THIS LINE OUT COMPLETELY, 
    // THE LOG STATEMENT INSIDE CURSOR.EACH ACTUALLY GETS LOGGED
    return Q.all(promises).then(callback(null, items));
  });
}

推荐答案

在不了解您在 cursor.each 循环中进行异步调用的详细信息的情况下,我将假定您拥有每次调用其中的函数完成其异步任务时都可以调用回调的功能:

Without knowing the details of the async calls you're making within the cursor.each loop, I shall assume that you have the ability to invoke a callback each time the functions invoked therein have completed their async task:

function doStuff() {
    var promises = [];  // array for storing promises

    cursor.each(function(err, blahblah) {
        var def = Q.defer();        // create deferred object and store
        promises.push(def.promise); // its promise in the array

        call_async_function(..., def.resolve);  // resolve the promise in the async function's callback
    });

    // pass the array to Q.all, only when all are resolved will "callback" be called
    return Q.all(promises);
} 

,用法变为:

doStuff().then(callback)

请注意,回调的调用现在永远不会触及 doStuff 函数-该函数现在还返回了promise.现在,您可以注册多个回调,失败回调等,而无需修改 doStuff .这称为关注点分离".

Note how the invocation of the callback now never touches the doStuff function - that function now also returns a promise. You can now register multiple callbacks, failure callbacks, etc, all without modifying doStuff. This is called "separation of concerns".

[NB:以上所有内容均基于Q promises库- https://github.com/kriskowal/q]

[NB: all the above based on the Q promises library - https://github.com/kriskowal/q]

EDIT 的进一步讨论和实验已经确定 .each 调用本身是异步的,并且当看到最后一行时,不向外界发出任何指示.我创建了一个要点,它可以解决此问题.

EDIT further discussion and experimentation has determined that the .each call is itself async, and gives no indication to the outside when the last row has been seen. I've created a Gist that demonstrates a resolution to this problem.

这篇关于Java语言如何在for循环完成后执行代码的文章就介绍到这了,希望我们推荐的答案对大家有所帮助,也希望大家多多支持IT屋!

查看全文
登录 关闭
扫码关注1秒登录
发送“验证码”获取 | 15天全站免登陆