WalzoneInterview Prep
📞 Interviewing soon? Practice with a realistic AI mock phone interview — it calls you, then scores you. First 15 min FREE →

Haskell · Advanced · question 55 of 100

Can you explain the differences between ’lazy’ and ’strict’ in Haskell?

📕 Buy this interview preparation book: 100 Haskell questions & answers — PDF + EPUB for $5

In Haskell, the terms ’lazy’ and ’strict’ refer to different evaluation strategies for function arguments.

Lazy Evaluation (also known as call-by-need or non-strict evaluation) is the default evaluation strategy in Haskell. It means that an expression is only evaluated when its value is actually needed for computation. If an expression is not used, it will not be evaluated at all. This allows Haskell to perform various optimizations and support infinite data structures.

Strict Evaluation (also known as call-by-value) is the counterpart where all function arguments are fully evaluated before the function is executed. In strict evaluation, an expression is always evaluated, even if it might not be needed later.

Here’s an example to illustrate the difference:

Consider the following Haskell function:

some_function a b = if a > 0 then a else b

When using lazy evaluation (the default in Haskell), if we call the function like this:

some_function 1 (1 `div` 0)

The function will return ‘1‘, despite having a potentially erroneous expression as the second argument, because the second argument is never evaluated (since ‘a > 0‘).

However, if the function were strict in both its arguments, the call would produce an error because Haskell would try to evaluate the expression ‘(1 ‘div‘ 0)‘ before invoking the function.

To make a function strict in Haskell, you can use ‘seq‘, ‘bang patterns‘, or the ‘strictness annotations‘ as follows:

1. Using ‘seq‘:

some_function a b = a `seq` b `seq` if a > 0 then a else b

2. Using ‘bang patterns‘:

{-# LANGUAGE BangPatterns #-}

some_function !a !b = if a > 0 then a else b

3. Using ‘strictness annotations‘:

{-# LANGUAGE Strict #-}

some_function a b = if a > 0 then a else b

To analyze the impact of strict and lazy evaluation, you can use evaluation trees. Given the function ‘f‘:

f x y = x*x + y*y

When evaluating ‘f (1+2) (2*3)‘ with lazy evaluation, the evaluation tree would look like this:

     f
    / 
   +   *
  /  / 
 1  2 2  3

Notice that values are only computed as needed.

On the other hand, if ‘f‘ were strict, we would need to evaluate all branches before invoking the function:

     f
    / 
   3   6
  /  / 
 1  2 2  3

In summary, the primary differences between lazy and strict evaluation in Haskell are:

1. Lazy evaluation evaluates expressions only when their values are needed, while strict evaluation evaluates all expressions before invoking functions.

2. Lazy evaluation can lead to potential time and space optimizations because unnecessary calculations are avoided.

3. Haskell supports infinite data structures thanks to lazy evaluation.

4. By default, Haskell uses lazy evaluation, but strictness can be introduced using language constructs such as ‘seq‘, bang patterns, or strictness annotations.

Reading is step one. Saying it out loud is the interview. Our AI interviewer calls your phone and runs a realistic Haskell interview — then scores it.
📞 Practice Haskell — free 15 min
📕 Buy this interview preparation book: 100 Haskell questions & answers — PDF + EPUB for $5

All 100 Haskell questions · All topics