1
$\begingroup$

An Alternative view of I/O programs, popular in earlier lazy functional programming languages, was to see the input and output as Strings, that is as lists of characters. Under that model an I/O program is a function

listIOprog :: Str->Str

This obviously makes sense in a 'batch' program, where al, the input is read before any output is produced but in fact it also works for interactive programs where input and output are interleaved, if the language is lazy. This is because in a lazy language we can began to print the result of a computation - the output of the interactive program here - before the arguement - the interactive input - is fully evaluated. As an example, repeadtely to rever lines of input under this model one can write

listIOprogram = unlines. map reverse . lines

I don't understand the bolded line. How can we evaluate the output before the actual inputs are given? For eg, take the function Sum x y = x+y, what would it mean to evaluate this without any numbers are given.

asked Feb 19, 2024 at 18:17
$\endgroup$

1 Answer 1

1
$\begingroup$

Addition is not a good example for this because it does need both of its inputs. Laziness comes into play for functions whose output may not depend on all of the input.

An example of laziness that can be found in virtually all mainstream programming languages is the boolean operator && (and its sibling ||). Conventionally, X && Y first evaluates the expression X, then if X is true, it evaluates Y. But if X is false, it skips evaluating Y, ignoring any of its side effects.

Lazy evaluation of the following program will interleave input (read_bool) and output (write_bool):

let x = read_bool() in
let y = read_bool() in
write_bool(x && y);
write_bool(y)

Lazy evaluation follows demand: we do not evaluate read_bool() immediately when we encounter the binding x = read_bool(), because x might not be needed in the end. Instead, write_bool is the operation that drives evaluation, because the value must be known before write_bool can print it.

The evaluation of that expression can be broken down as follows, with IO operations written in bold.

  1. write_bool(x && y) demands x && y
  2. x && y demands x
  3. x = read_bool() reads a boolean. For example, x = false. Now we can go back to the previous expression that demanded x.
  4. false && y = false (by definition of &&).
  5. write_bool(false) writes false.
  6. write_bool(y) demands y
  7. y = read_bool() reads a boolean. For example, y = true.
  8. write_bool(true) writes true.

That is how lazy evaluation lets us interleave IO operations even though in the source expression, all input operations appeared before all output operations.

answered Feb 20, 2024 at 20:56
$\endgroup$

Your Answer

Draft saved
Draft discarded

Sign up or log in

Sign up using Google
Sign up using Email and Password

Post as a guest

Required, but never shown

Post as a guest

Required, but never shown

By clicking "Post Your Answer", you agree to our terms of service and acknowledge you have read our privacy policy.

Start asking to get answers

Find the answer to your question by asking.

Ask question

Explore related questions

See similar questions with these tags.