A Note on Lazy Evaluation in R

R is commonly thought of as a functional programming language. If you associate functional programming (FP) with lambda calculus and pure FP languages like Haskell, then you may get surprised by aspects of R’s computational model. One of these has to do with R’s lazy evaluation mechanism, in particular the concept of “promise objects” (as pointed out by some, R passes a promise, not a value).

Here’s a simple program to illustrate what I mean.

add <- function(x) { function(y) x + y } 
adders <- lapply(1:10, add)

What would you expect to be the answer for the following two queries?

adders[[1]](10)
adders[[10]](10)

It turns out both evaluate to 20, when one expects 11 and 20!

Contrary to what one would expect from lambda calculus, the x in the closure of both adders[[1]] and adders[[10]] are bound to 10, the last value of the vector 1:10, as seen below:

as.list(environment(adders[[1]]))
$x
[1]10

as.list(environment(adders[[1]]))
$x
[1]10

There is further discussion of this issue at http://stackoverflow.com/questions/29084193/how-to-not-fall-into-rs-lazy-evaluation-trap


Leave a Reply

Fill in your details below or click an icon to log in:

WordPress.com Logo

You are commenting using your WordPress.com account. Log Out /  Change )

Facebook photo

You are commenting using your Facebook account. Log Out /  Change )

Connecting to %s