Haskell: Comment tuyau le contenu d'une poignée dans une autre en temps réel
Question
Je suis en train d'écrire un programme qui fonctionne de manière interactive un sous-processus externe et j'ai besoin le contenu de la poignée de sortie pour être STDOUT dès qu'il est disponible. J'ai essayé quelque chose comme ceci:
main = do processInfo <- createProcess (proc "ghci" []){std_out = CreatePipe,
std_in = CreatePipe }
case processInfo of
(Just hIn, Just hOut, _, _) -> do mainloop hIn hOut
hClose hIn
hClose hOut
_ -> do error "Unable to start process"
mainloop :: Handle -> Handle -> IO ()
mainloop inh outh =
do ineof <- hIsEOF outh
if ineof
then return ()
else do inpStr <- hGetLine outh
putStrLn inpStr
mainloop inh outh
Mais cela ne fonctionne pas, car il ne reconnaît que la ligne de sortie par ligne, de sorte que toute sortie sur le processus poignée de sortie qui ne se termine pas par un saut de ligne ne se présente pas. J'ai essayé la même chose avec hGetContents mais elle produit le même résultat. J'ai lu dans la documentation des deux système.Procédé et System.IO et n'ont pas vraiment trouvé rien de concluant.
La solution
hSetBuffering
est ce que vous cherchez, la valeur par défaut (sous Unix au moins) est mise en mémoire tampon de ligne. Il permet à l'entrée standard avant de commencer la boucle principale
hSetBuffering hIn NoBuffering
et éventuellement aussi sur la poignée de sortie si vous voulez voir les résultats immédiatement sur le côté de sortie. Notez toutefois que la désactivation de mise en mémoire tampon peut diminuer considérablement les performances tout à fait.
Autres conseils
Je suis un débutant beaucoup Haskell, mais je me souviens à venir à travers un exemple récemment de traitement de caractère par caractère d'entrée. hSetBuffering peut-être ce que vous cherchez?
est Buffering une chose, mais vous utilisez aussi qui attendra gGetLine
pour une ligne entière (ou la fin du fichier). Pensez à utiliser si vous voulez hGetChar
vraiment lire un caractère à l'époque.
Et d'ailleurs, une autre façon de surmonter en mémoire tampon est d'utiliser hFlush
.