Take the 2-minute tour ×

Is it possible to turn off lazy evaluation in Haskell?

Is there a specific compiler flag of library to facilitate this?

I wanted to try something new with a old program that I had written a while back, to see if I can profile better it or optimize it further.

share|improve this question
It's part of the language pal, down at the deepest level. Is there something specific that you want to be eager? –  bchurchill Mar 26 '13 at 1:46
Is it possible to turn off strict evaluation in, say, C? I hope not, at least not without some serious redesign of the language semantics down to the deepest level. Of course, it is possible to implement some kind of lazy evaluation for specific expressions in C. All of those statements are true for Haskell, too, except with "strict" and "lazy" interchanged. –  Yitz Mar 27 '13 at 13:56
@Yitz - real world computers use strict evaluation. Compilers don't need to work hard to evaluate strictly - they need to work hard (adding thunks, deferring evaluation, strictness analysis to determine where that's not necessary) to support laziness. It took GHCs authors a very long time to control those overheads and, despite that, a strict language is more referentially transparent than a lazy version of the same language - laziness means that time and space complexity aren't referentially transparent due to deferred computations and the mutable data structure used to keep track of them. –  Steve314 Mar 30 '13 at 11:34
@Yitz - pervasive lazy evaluation is particularly a problem in interactive and real-time programs. Instead of doing work when there's plenty of time available, laziness defers that work until the result is needed - by definition, when it's already too late. There are workarounds in Haskell with selective strictness, of course, but that's not trivial - e.g. $! only forces the strict parameter to head-normal form - use it for a list and the members of that are still evaluated lazily. –  Steve314 Mar 30 '13 at 11:40
@Steve314 - No, real computers use whatever semantics your compiler compiles them down to. At the hardware level, the semantics of modern processors are almost as far from the imperative model of C as they are from the non-strict model of Haskell. In any mature language, an experienced programmer can optimize down to whatever level is needed to match the hardware platform while still benefiting as much as possible from the strengths of the language, and Haskell is no exception. It's no harder in Haskell than it is in C. –  Yitz Apr 28 '13 at 14:12
show 7 more comments

6 Answers

up vote 27 down vote accepted

There are a number of ways to turn a lazy thing strict. You can:

  1. Explicitly insert a spurious pattern match.
  2. Use seq or its close relative ($!).
  3. Use BangPatterns.
  4. Use strictness annotations on your types.

More information here.

share|improve this answer
What is a spurious pattern match? –  Nikita Volkov Mar 26 '13 at 8:10
@NikitaVolkov For example, for lists, replacing foo with case xs of [] -> foo; _:_ -> foo. –  Daniel Wagner Mar 26 '13 at 11:32
Using seq or $! doesn't force a whole expression to be fully evaluated - it only forces "head normal form". For example, use seq on your list computation and it will eagerly evaluate the result list - but that's just which "cons" holds the head item of the list. The head member and the entire tail list may not have been evaluated yet. To force a complete expression to be fully evaluated, one option is deepseq, which means you need to instance the NFData typeclass. Another is a strictness-forcing function tailored for the result type. –  Steve314 Mar 27 '13 at 11:16
the strict Data.ByteString is another –  pyCthon Apr 7 '13 at 6:12
add comment

You can't turn off laziness, because the I/O system of Haskell depends on it. Without lazy evaluation this program would run into a busy loop without ever outputting anything:

main = forever (putStrLn "Hello!")

This is because forever c is an infinite program. With lazy evaluation the program is calculated only as far as necessary to run the next instruction. If you turn off laziness, every function becomes strict, including (>>), which basically makes the forever function diverge:

forever c = let cs = c >> cs in cs

However, you can add strictness annotations to constructors and patterns. When a function is strict, its argument is forced as part of the evaluation of the result independent of whether the argument is needed or not. This resembles eager evaluation.

share|improve this answer
This doesn't prove you can't turn off laziness - it only proves that the set of programs where you can turn off laziness and still have them work is heavily constrained. forever is just a particularly obvious problem function - there are many less obvious ones that would cause similar problems - but a sufficiently obsessive person might be able to identify and work with a Haskell subset that still works with laziness disabled. +1 anyway - that's still a good point. –  Steve314 Mar 27 '13 at 11:23
You could define forever as forever c = c >>= \_ -> forever c which will work even with strict evaluation. –  Twan van Laarhoven Mar 27 '13 at 14:14
add comment

In addition to what Daniel Wagner listed you may want to take a look at a similar question Is there a Haskell compiler or preprocessor that uses strict evaluation?.

  • Answers include the DDC compiler which attempts to make an strict version of haskell and only lazy explicitly
  • ghc plugin described in monad.reader 12
  • "Using nfdata and rnf everywhere" - solrize
  • and more

The predominate suggestion is to use profiling tools and learn how to optimize Haskell as it is however, since most would consider it a different language with non-strict evaluation turned off.

share|improve this answer
add comment

There's a variant of Haskell called pH (http://csg.csail.mit.edu/projects/languages/ph.shtml) which uses eager evaluation while still providing non-strict semantics. The Haskell Report is careful to say that it's a non-strict language. Laziness is the obvious way to describe and, apparently, to implement non-strictness.

So, if your question is "Can we use a different evaluation system while maintaining non-strict semantics", you could look at pH. If your question is "Is there a version of Haskell which shares the surface syntax but is strict by default", I think it's covered by other answers.

share|improve this answer
add comment

The simple answer is no. The more complex answer is that the computational model upon which Haskell builds up and evaluates functions works in a lazy manner. As you will read in other answer there are ways to force evaluation of some functions earlier then normal, and it is occasionally adventitious to do so. But there is a large portion of valid Haskell which has no normal form. This includes the IO functions and a large amount of the standard prelude.

Conclusion: there is no more a way to turn of lazy evaluation in Haskell then there is a way to turn off pointer arithmetic in C or to turn off OO in Ruby of Java. I suspect that this is much farther then you though this question would take you. (There's no --strict mode), but if you really want to see just how deep the rabit hole goes, "Implementing Lazy Functional Languages on Stock Hardware: The Spineless Tagless G-machine" by Simon Peyton Jones is an adventure worth having.

share|improve this answer
Do you have an updated link for that paper? The one listed is broken. –  jrk Mar 27 '13 at 13:21
add comment

The strict-identity package has a strict version of the Identity monad.

You can find it here: https://hackage.haskell.org/package/strict-identity

The usage would look something like this:

foo = runStrictIdentity $! do
    x <- f a b
    y <- g x y
    return $! x + y

Each time return or bind >>= is used, the two parts are evaluated using seq, giving a reasonable guarantee of strictness provided your data structure isn't too deep. This works, for i.e. numbers and basic structures.

share|improve this answer
add comment

Your Answer


