Lazy IO is useful! [Was: "interact" behaves oddly...]

Thomas Hallgren hallgren at cse.ogi.edu
Wed Oct 1 16:07:05 EDT 2003


Simon Marlow wrote:

>The real problem is that lazy I/O injects side effects into the pure
>world of expressions.  Haskell has a perfectly good system for
>encapsulating side effects - the IO monad.  So why put these sneaky side
>effects into pure values?
>  
>
Although monadic IO is nice in many ways, I think of its introduction in 
Haskell as a stopgap measure that solved the immediate problem of 
interfacing Haskell to traditional operating system's imperative APIs, 
but at the same time seems to have put a stop to further research into 
the proper integration of laziness and IO.
 
Laziness makes computation demand-driven and allows us to abstract away 
the order of evaluation. We think this is useful (most of the time) and 
that's why Haskell is a lazy language.

Demand-driven IO is useful too: sometimes, but not always, it is useful 
to abstract away from the exact details of when IO happens.

For example, laziness should allow the following Haskell program to run 
in constant space, although it makes use of a large intermediate structure:

main = let mylist = [1..10000]
               result = sum mylist
           in print result

Now suppose that for some reason that instead of processing the large 
intermediate structure directly, I need to store it in a file and 
process it later, with a program like this:

main =
  do let mylist = [1..10000]
     writeFile "myfile.txt" (unlines (map show mylist))
--   ...
     mylist' <- (map read . lines) `fmap` readFile "myfile.txt"
     let result = sum mylist'
     print result

With lazy IO, this program too should run in constant space, and the 
functions that consume the large intermediate structure can remain 
unchanged!

So, I think a lazy programming language should support not only lazy 
evaluation, but also lazy IO! When it is appropriate to abstract away 
from the details of when IO happens, lazy IO is useful. It can 
facilitate separation of concerns and modularity, just like lazy 
evaluation. Appropriate lazy IO should not compromise the purity of the 
language or be an obstacle to optimistic evaluation. Instead of settling 
for the monadic stopgap IO, we should continue to look for good ways to 
integrate laziness and IO!

-- 
Thomas H

"Delay is preferable to error."
  - Thomas Jefferson (3rd President of the United States)




More information about the Haskell-Cafe mailing list