{-# language DeriveFunctor #-}
data IOpure a
= Return a
instance Applicative IOpure where
pure = Return
(<*>) = ap
instance Monad IOpure
where Return x >>= f = f x
Output s io >>= f = Output s (io >>= f)
Input k >>= f = Input (\s -> k s >>= f)
class Monad m
=> Interaction m
where produceOutput
:: String -> m
()
instance Interaction IOpure where
getInput = Input Return
produceOutput x = Output x (Return ())
echoingUser :: IOpure a -> a
echoingUser = go "no output"
where
go _ (Return x) = x
go _ (Output o io) = go o io
go o (Input k) = go o (k o)
interactiveProgram = do
produceOutput "Jeff"
name <- getInput
produceOutput "Bob"
name2 <- getInput
main
= print (echoingUser interactiveProgram
)
ey0jIGxhbmd1YWdlIERlcml2ZUZ1bmN0b3IgIy19CgppbXBvcnQgQ29udHJvbC5Nb25hZAoKZGF0YSBJT3B1cmUgYSAKICA9IFJldHVybiBhCiAgfCBPdXRwdXQgU3RyaW5nIChJT3B1cmUgYSkKICB8IElucHV0IChTdHJpbmcgLT4gSU9wdXJlIGEpCiAgZGVyaXZpbmcgRnVuY3RvcgoKaW5zdGFuY2UgQXBwbGljYXRpdmUgSU9wdXJlIHdoZXJlCiAgIHB1cmUgPSBSZXR1cm4KICAgKDwqPikgPSBhcAoKaW5zdGFuY2UgTW9uYWQgSU9wdXJlIHdoZXJlCiAgIFJldHVybiB4ID4+PSBmID0gZiB4CiAgIE91dHB1dCBzIGlvID4+PSBmID0gT3V0cHV0IHMgKGlvID4+PSBmKQogICBJbnB1dCBrID4+PSBmID0gSW5wdXQgKFxzIC0+IGsgcyA+Pj0gZikKICAgCmNsYXNzIE1vbmFkIG0gPT4gSW50ZXJhY3Rpb24gbSB3aGVyZQogIGdldElucHV0IDo6IG0gU3RyaW5nCiAgcHJvZHVjZU91dHB1dCA6OiBTdHJpbmcgLT4gbSAoKQoKaW5zdGFuY2UgSW50ZXJhY3Rpb24gSU9wdXJlIHdoZXJlCiAgZ2V0SW5wdXQgPSBJbnB1dCBSZXR1cm4KICBwcm9kdWNlT3V0cHV0IHggPSBPdXRwdXQgeCAoUmV0dXJuICgpKQoKZWNob2luZ1VzZXIgOjogSU9wdXJlIGEgLT4gYQplY2hvaW5nVXNlciA9IGdvICJubyBvdXRwdXQiCiAgIHdoZXJlCiAgIGdvIF8gKFJldHVybiB4KSAgICA9IHgKICAgZ28gXyAoT3V0cHV0IG8gaW8pID0gZ28gbyBpbwogICBnbyBvIChJbnB1dCBrKSAgICAgPSBnbyBvIChrIG8pCgppbnRlcmFjdGl2ZVByb2dyYW0gOjogSW50ZXJhY3Rpb24gbSA9PiBtIChTdHJpbmcsIFN0cmluZykKaW50ZXJhY3RpdmVQcm9ncmFtID0gZG8KICBwcm9kdWNlT3V0cHV0ICJKZWZmIgogIG5hbWUgPC0gZ2V0SW5wdXQKICBwcm9kdWNlT3V0cHV0ICJCb2IiCiAgbmFtZTIgPC0gZ2V0SW5wdXQKICByZXR1cm4gKG5hbWUsIG5hbWUyKQoKbWFpbiA6OiBJTyAoKQptYWluID0gcHJpbnQgKGVjaG9pbmdVc2VyIGludGVyYWN0aXZlUHJvZ3JhbSkK