2016-07-10 12 views
0

Ich habe ein Beispielcode und Ausgänge sind wie folgt: Code:Wie Callback-Funktion in NodeJs funktioniert?

for(var i = 0; i <20; i++) { 
    var fs = require("fs"); 

    fs.readFile('input2.txt', function (err, data) { 
     if (err) return console.error(err); 
     console.log("first started\n"); 
     console.log(data.toString()); 
    }); 

    console.log("first Ended"); 

    console.log("second started"); 
    var data = fs.readFileSync('input1.txt'); 

    console.log(data.toString()); 
    console.log("second Ended"); 
} 

Output:

Ended ersten zweiten begonnen zweiten zweiten Ended ersten Ended begonnen und so weiter bis 20 mal first started d
begann 1 und so weiter bis 20mal

Als input2.txt nur ein Zeichen in ihm hat und input1.txt hat keine Zeilen drin. Ich ging davon aus, dass die Callback-Funktion nach dem Drucken der Eingabe aus der ersten Datei nach einer Iteration aufgerufen würde, da die Dateileseoperation zu diesem Zeitpunkt abgeschlossen sein sollte. Aber das ist nicht der Fall. Bedeutet, dass der Synchronisierungsvorgang zuerst abgeschlossen wird und nur Callback funktioniert. Wie wäre das möglich? Wenn Callback so lange warten soll, was ist der Zweck des asynchronen Aufrufs hier?

+0

Denken Sie an 'fs.readFile (...)' 'wie setTimeout (...)'. Wenn Sie verstehen, wie und warum 'setTimeout()' darauf wartet, dass der aktuelle Ausführungs-Tick abgeschlossen wird, bevor der Callback erfolgt, sollten Sie verstehen, dass 'fs.readFile()' genau so funktioniert, außer dass die Zeit des Callbacks abgelaufen ist tritt in Abhängigkeit davon auf, wie lange es dauert, die Datei zu lesen, anstatt wie viele Millisekunden Sie angeben. –

Antwort

0

Ihre for Schleife läuft synchron zur Fertigstellung und startet 20 fs.readFile() Operationen, die alle asynchron sind (dh sie werden später beendet).

Dann, nachdem die for Schleife beendet ist, beginnen die asynchronen Operationen zu beenden und werden nacheinander bedient (nicht unbedingt in der Reihenfolge, in der sie gestartet wurden).

Da Ihr eigenes Javascript in node.js single threaded ist, bedeutet dies, dass Ihr aktueller Ausführungs-Thread vollständig ausgeführt wird, sodass die for-Schleife ausgeführt wird, bis sie fertig ist. Jede Iteration der for-Schleife startet eine fs.readFile()-Operation, die asynchron ist. Dieser Vorgang wird dann im Hintergrund ausgeführt, während die for Schleife fortgesetzt wird. Wenn jede Operation fs.readFile() abgeschlossen ist, wird ihr Rückruf der JS-Ereigniswarteschlange hinzugefügt. Wenn der aktuelle Ausführungsthread beendet ist (und nur dann), zieht der Javascript-Interpreter das erste Element aus der Ereigniswarteschlange und führt es aus (wenn sich an dieser Stelle irgendetwas in der Ereigniswarteschlange befindet). Wenn sich zu diesem Zeitpunkt nichts in der Ereigniswarteschlange befindet (weil keine der asynchronen Operationen noch nicht abgeschlossen ist, wartet die JS-Engine auf das nächste Ereignis, und wenn die erste asynchrone Operation abgeschlossen ist und einen Rückruf in die Ereigniswarteschlange einfügt, dann

Asynchrone Callbacks wie diese werden nie mitten in einem ausgeführten Javascript aufgerufen JS ist single threaded, so dass diese asynchronen Callbacks erst im aktuellen Thread aufgerufen werden . von JS beendet

Obwohl diese Antwort für Ajax geschrieben wurde ruft im Browser, ist die Ereigniswarteschlange Konzept das gleiche in node.js so könnte dies auch erklären helfen: How does JavaScript handle AJAX responses in the background?

0

Wenn eine Funktion namens async aufgerufen wird, ruft ihr Callback den nächsten Tick in node.js

In Ihrem Snippet werden alle Anweisungen in der Schleife aufgerufen und ausgeführt. Aber dieser Callback, um Async-Datei zu lesen, setzt in die nächste Tick-Warteschlange, um ausgeführt zu werden.

Bitte schauen Sie auf Process.nextTick

Verwandte Themen