Waiting on two inputs in Haskell, simultaneously
concurrency, haskell, io
Solution
I don't think "using a single thread" makes sense here. You must already be using multiple Haskell threads anyway to write to the `TChan`. You should use two Haskell threads to do this, and use an `MVar` or similar to communicate the first result to arrive. For example:
module Main where
import System.IO
import Control.Concurrent
import Control.Concurrent.MVar
import Control.Concurrent.STM
import Control.Concurrent.STM.TChan
main = do
chan <- newTChanIO
forkIO (threadTChanWrite chan)
threadMultiplexedRead chan
threadTChanWrite chan = do
threadDelay 5000000
atomically $ writeTChan chan 3
threadMultiplexedRead chan = do
mvar <- newEmptyMVar
forkIO (threadKeyboardRead mvar)
forkIO (threadTChanRead mvar chan)
v <- readMVar mvar
print v
threadKeyboardRead mvar = do
str <- getLine
putMVar mvar (Right str)
threadTChanRead mvar chan = do
v <- atomically (readTChan chan)
putMVar mvar (Left v)
A proper implementation would probably clean up the threads left lying around afterwards, btw.
Problem
The title may be a bit vague. This is what I mean: Say I have two ways of getting input to my program. The first is via the keyboard, using the function `getLine` which blocks until a line is read. The other is, say, via a `TChan`, where using `readTChan chan` will also result in a block until a value is present in the channel, whereupon it will be read. What I want to accomplish is being able to wait for both values, using a single thread and not allowing my CPU to jump to 100%. The moment one of the two values is available, it is fetched and the program resumes. (Say, using `Either` to notify which of the two values was received.) Is this possible? Thank you very much!