2013-07-12 6 views
-1

В примере:Почему async node.js ведет себя странно?

async.eachLimit([1,2,3,4,5,6,7,8,9,10], 6, function(a, b) { 
    console.log("current: " + a); 
    b("done"); 
    }, 
    function(err) { 
    if (err) { 
     console.log("error"); 
    } else { 
     console.log("completely done"); 
    } 
    } 
); 

Выход:

current: 1 
error 
current: 2 
current: 3 
current: 4 
current: 5 
current: 6 
undefined 

Почему такое странное поведение? Где происходит ошибка и неопределенность? И где обрабатываются остальные 4 элемента? Когда вызывается обратный вызов async? Как и следовало ожидать от меня:

current: 1 
done 
current: 2 
done 
current: 3 
done 
current: 4 
done 
current: 5 
done 
current: 6 
done 
current: 7 
done 
current: 8 
done 
current: 9 
done 
current: 10 
done 
compeletely done 

Так что только 6 элементов активны одновременно.

Что я должен изменить, чтобы получить поведение async, как я ожидал?

Update:

и если я использую

async.**eachSeries**([1,2,3,4,5,6,7,8,9,10], function(a, b) { 
    console.log("current: " + a); 
    b("done"); 
    }, 
    function(err) { 
    if (err) { 
     console.log("error"); 
    } else { 
     console.log("completely done"); 
    } 
    } 
); 

, то выход странно тоже:

current: 1 
error 
undefined 
+0

Вы не печатаете 'done' только' compeletely done' в конце. См. Ответ Джонатана о том, почему он терпит неудачу. – user568109

ответ

2

Много проблем проистекают из этой линии:

b("done"); 

Это устанавливает "done" как err так that's what the 1st arguments is:

передается итератор callback(err), который должен быть вызван, как только он закончил. Если ошибка не была выполнена, обратный вызов должен запускаться без аргументов или с явным аргументом null.

На основе результатов вы перечислили, как и ожидалось, вы, вероятно, хотели:

console.log("done"); 
b(null); // or: `b()` 

  1. Где приходит сообщение об ошибке и неопределенными из?

    error происходит от callback:

    if (err) { 
        console.log("error"); 
    } 
    

    undefined, однако, не из сниппета. Хотя, если вы используете интерактивный REPL Node, тогда это будет источник, так как он отобразит eachLimit значение return (что равно undefined).

  2. Когда вызывается обратный вызов async?

    При передаче errcallback называется ранним.

  3. А где остальные 4 элемента обработаны?

    После того, как err был отправлен, функции async прекратят итерацию. eachLimit только делает это 6, потому что он хочет закончить текущий «пакет» перед остановкой.


Что касается eachLimit() против eachSeries(), что зависит от того, что делает iterator. В настоящее время iterator является полностью синхронным, поэтому обе функции будут работать довольно точно - итерируя 1 значение за раз.

И, чтобы быть ясным: библиотека async не может выполнять синхронные задачи асинхронно. Он фактически предполагает, что задачи уже асинхронны и просто помогает управлять группой из них.

Смежные вопросы