node.js中的函數是同步的或異步的。同步碼在一個線程中運行,因而表現得完全像你使用的代碼:
fn1();
fn2();
fn3(fn4());
將運行fn1
,然後fn2
,然後fn4
,然後fn3
(在fn4
結果作爲參數傳遞) 。
異步代碼引發了一些操作,並將其作爲參數執行時執行的函數(這可能會反過來引發另一個異步操作)。你立即得到控制權。例如:
doSomeAsyncThing(function() {
console.log("did the async thing");
});
console.log("hello");
執行方式如下:首先,打開異步操作,然後打印「hello」。一段時間後,異步操作完成,因此調用回調,並打印「異步事件」。
如果你想要做一個異步的事情,然後做另一件事異步第一個完成後,以標準的方式是窩的回調:
async1(function() {
async2(function() {
console.log("async1 and async2 finished");
});
});
雖然there是better選項。
所以在第二個例子中,如果fn1
是同步的,它將完全按照您所寫的完全一樣。如果fn1
必須做一些事情異步,它也必須是異步的,所以你必須把它寫這樣的:
function fn1(callback) {
// do some sync stuff
doSomethingAsync(function() {
// do more sync stuff
doSomethingMoreAsync(function() {
// do more sync stuff
callback(); // call the callback once everything is completed
});
});
}
然後調用它像這樣
fn1(function() {
fn2();
});
這可以簡化到:
fn1(fn2);
在你的第一個例子中,請注意array.forEach是同步的。如果你的// do many many things
都是同步的,那麼它就會像你寫的一樣工作,但是如果在那裏有一個異步操作,你可以手動實現一個計數器,或者只使用async庫或Promise iterator utilities。
*只有在'forEach'循環結束後,您才能*聽'stdin'上的'input'事件。由於你的問題是關於異步行爲的,你需要向我們展示*你實際調用的異步函數。請發佈「許多東西」和「長長碼」的相關部分! – Bergi