Ich habe diese Frage gefunden, die fragt, wie man asynchrone Eingaben liest, aber nur Arbeiten Sie mit POSIX-Stream-Deskriptoren, die unter Windows nicht funktionieren. Also habe ich dieses Tutorial gefunden, das zeigt, dass anstelle eines POSIX Stream Descriptor Ich kann ein boost::asio::windows::stream_handle
verwenden.
Nach beiden Beispielen kam ich auf den folgenden Code. Wenn ich es ausführe, kann ich nichts in die Eingabeaufforderung eingeben, da das Programm sofort beendet wird. Ich möchte, dass es jede Eingabe vom Benutzer erfasst, möglicherweise in eine std::string
, während andere Logik in meinem Programm ausgeführt werden kann (d. H. Asynchrone I / O von einer Windows-Konsole ausführen).
Im Wesentlichen versuche ich zu vermeiden, mein Programm zu blockieren, wenn es versucht, von stdin
zu lesen. Ich weiß nicht, ob das in Windows möglich ist, da ich auch diesen Beitrag gefunden habe Details zu Problemen, mit denen ein anderer Benutzer bei der gleichen Vorgehensweise konfrontiert wurde.
Ich habe gerade ein oder zwei Stunden damit verbracht, dieses Thema zu untersuchen, also habe ich beschlossen zu schreiben, um andere daran zu hindern, ihre Zeit zu verschwenden.
Windows unterstützt IOCP für standardmäßige Eingabe- / Ausgabehandles nicht. Wenn Sie das Handle von GetStdHandle(STD_INPUT_HANDLE)
übernehmen, enthält das Handle FILE_FLAG_OVERLAPPED
nicht, sodass es überlappende (asynchrone) IO nicht unterstützt. Aber selbst wenn du
WinAPI ignoriert dwFlagsAndAttributes
und gibt das Handle zurück, das überlappende IO nicht unterstützt. Die einzige Möglichkeit, asynchrone IO der Konsoleneingabe / -ausgabe zu erhalten, besteht darin, das Handle mit WaitForSingleObject
mit 0-Timeout zu verwenden, damit Sie überprüfen können, ob etwas nicht blockierend gelesen werden kann. Nicht genau async IO aber kann Multithreading vermeiden, wenn es ein Ziel ist.
Weitere Details zur Konsolen-API: Ссылка
Was ist der Unterschied zwischen Handles, die von GetStdHandle
und CreateFile
zurückgegeben werden, wird hier beschrieben: Ссылка . Kurz gesagt ist der Unterschied nur für einen untergeordneten Prozess, wenn CreateFile
Zugriff auf seinen Konsolen-Eingabepuffer geben kann, selbst wenn er im übergeordneten Prozess umgeleitet wurde.
Sie müssen io_service::run()
auf starten die Ereignisverarbeitungsschleife für asynchrone Operationen.
Sie müssen Ihren stream_handle mit dem Konsoleneingabe-Handle initialisieren. Sie können nicht denselben stream_handle für die Eingabe und für die Ausgabe verwenden, da dies zwei verschiedene Handles sind.
Für die Eingabe:
%Vor% Für die Ausgabe würden Sie CONSOLE_OUTPUT_HANDLE
verwenden. Aber das ist wahrscheinlich zu viel Aufwand, Sie werden wahrscheinlich nicht so viele Daten in Windows ausgeben, dass Sie einen asynchronen Schreibvorgang benötigen.
Tags und Links c++ windows boost boost-asio