Is Elm lazy?

Skip to first unread message

Dylan Just

Mar 9, 2013, 6:28:14 AM3/9/13
Just looking to encode a cyclic linked list/signal - laziness makes this much easier.

Jeff Smits

Mar 9, 2013, 9:14:16 AM3/9/13
Nope, Elm is not lazy. 
Don't know if that's a choice Evan made because JS is the compiler's target language or because of other reasons...

John Mayer (gmail)

Mar 9, 2013, 10:25:28 AM3/9/13
His thesis mentions two reasons. Small reason - JS is strict. Big reason - FRP and laziness tend not to play well together. A lot of research went into fixing all the time and space leaks, but added a lot of complexity. 

Sent from my iPhone
You received this message because you are subscribed to the Google Groups "Elm Discuss" group.
To unsubscribe from this group and stop receiving emails from it, send an email to
For more options, visit

Evan Czaplicki

Mar 9, 2013, 1:58:48 PM3/9/13
Trade-offs! Yes, FRP and concurrency are the main reasons. Also personal preference. In an interactive system, I do not think waiting to perform a computation until later is the right default (more background). foldp is the major reason in FRP.

In a concurrent system, you also run into majorly annoying things (in my opinion). For example, say you have the following actors and communication channels:

|   |
F   G
 \ /

Each node (F, G, H) are all doing some computation, and F and G are supposed to run concurrently. Things in F do not block things in G. Say computation F happens to be very expensive, taking a noticeable amount of time. That's fine, it does not block G right? In a lazy system, the default is, pass the unevaluated expression across every channel, so the computations escape! So everything ends up happening in H and F blocks G!

So for any FRP or concurrent program you write, you get to use laziness at its worst (in my opinion). In Elm, that is every program.

If you want to argue that adding strictness annotations is no big deal or something, I'd rather not. I've had that discussion elsewhere and can probably find a link to it.

Dylan Just

Mar 9, 2013, 4:49:49 PM3/9/13
Cool. Just needed to know. 

Franco Bulgarelli

Oct 24, 2013, 10:03:42 AM10/24/13
Hi Evan!

Just curious, why don't doing the opposite - preserving the strict semantics by default, but adding laziness annotations?

If that is also covered in the discussion you mentioned, could please provide that link?

Thanks in advance!

Evan Czaplicki

Oct 24, 2013, 12:00:37 PM10/24/13
to, Dylan Just
I don't understand the question. It is strict by default. In theory, maybe it is possible to add a "this file is lazy" annotation, but Haskell people tend to not think so. You can definitely model laziness in a strict language. Haskell people say that's not enough and Clojure people say it works amazingly (their containers like lists and dicts all use lazy data structures, but the language is still strict).

I think the conversations I was talking about happened on reddit. I'm not really sure how to find them besides crawling through old posts by wheatBread.

Raoul Duke

Oct 24, 2013, 12:13:39 PM10/24/13
to elm-discuss
> language. Haskell people say that's not enough and Clojure people say it
> works amazingly (their containers like lists and dicts all use lazy data
> structures, but the language is still strict).

except for all the times it doesn't (see the long history of 'why
doesn't this work? ... oh because it is/not lazy!" questions). :-)

Max New

Oct 24, 2013, 5:09:26 PM10/24/13
Laziness is easy to implement in a strict language using thunks (() -> a) described well in SICP:

I implemented this in Elm a while ago:

But if you run main.elm the performance is pretty crappy. There are a couple possibilities as to why, and someone could probably use a profiler to find out which one but I tried it with the chrome profiler and didn't understand it. Anyway, it could be that the overhead of the extra function calls from the thunks is the main reason, but another problem is that thunks are not memoized so a lot of things are recomputed. In an impure language this can be done by the programmer, and in Haskell this is baked into the compiler, but in Elm you don't get this ability.

The options for laziness in Elm would then be as follows:
1. Use thunks as they are and work around crappy performance (limiting expressiveness :( )
2. Write a memoizing thunk library using the JS FFI (probably not a bad idea, I might actually do this to see the performance)
3. Add laziness annotations to the language. (Very heavyweight and probably low priority, also might run into problems with impure signal creation?)

Do Bi

Oct 30, 2013, 3:43:25 PM10/30/13
Can somebody explain to me, why the following does not crash, even though Elm is not lazy? :-)

bottom = (let x = x in x)
const a b = a
main = asText <| const 1 bottom


Max New

Oct 30, 2013, 3:54:31 PM10/30/13
The generated code just evaluates to undefined in javascript:

             var bottom = function ()
                            var x = x;
                            return x

Directly printing it isn't an infinite loop either.

-Max Stewart New

You received this message because you are subscribed to a topic in the Google Groups "Elm Discuss" group.
To unsubscribe from this topic, visit
To unsubscribe from this group and all its topics, send an email to

Joseph Collard

Oct 30, 2013, 3:56:31 PM10/30/13
I have a feeling that bottom is being turned into a function. This means that until you actually do function application on it, it never executes anything.


Do Bi

Oct 30, 2013, 4:02:12 PM10/30/13
Ah, thanks. So it is just a Javescript property, and nothing one should count on when writing Elm code, that should work even in the distant future. ;)

Dénes Harmath

May 26, 2015, 8:05:27 AM5/26/15
@Max: Thank you for mentioning thunks, linking SICP and creating the memoization library! My application has recursive values which requires lazyness, and these helped enormously to implement it!
Reply all
Reply to author
0 new messages