[Rd] merging environments

Gabor Grothendieck ggrothendieck at gmail.com
Fri Mar 7 21:47:17 CET 2008


On Fri, Mar 7, 2008 at 3:15 PM, hadley wickham <h.wickham at gmail.com> wrote:
> 2008/3/7 Ben Bolker <bolker at zoo.ufl.edu>:
> >
>
> >    Despite the spirited arguments of various R-core folks
> >  who feel that mle() doesn't need a "data" argument, and
> >  that users would be better off learning to deal with function
> >  closures, I am *still* trying to make such things work
> >  in a reasonably smooth fashion ...
> >
> >    Is there a standard idiom for "merging" environments?
> >  i.e., suppose a function has an environment that I want
> >  to preserve, but _add_ the contents of a data list --
> >  would something like this do it? Is there a less ugly
> >  way?
> >
> >  x <- 0
> >  y <- 1
> >  z <- 2
> >
> >  f <- function() {
> >      x+y+z
> >  }
> >
> >  f2 <- function(fun,data) {
> >      L <- ls(pos=environment(fun))
> >      mapply(assign,names(data),data,
> >                       MoreArgs=list(envir=environment(fun)))
> >      print(ls(pos=environment(fun)))
> >  }
> >
> >  f2(f,list(a=1))
>
> I think you're doomed to be ugly if you don't use closures - I think
> any explicit manipulation of environments is worse than the implicit
> manipulation by closures.
>
> f <- function(data) with(data, x + y + z)
> f2 <- function(fun, data) function() fun(data)
>
> f2(f, list(x = 10))()
>
> Although it would be even nicer if you could do:
>
> f <- function()  x + y + z
> f2 <- function(fun, data) function() with(data, fun())


This last one is close to what you can do with proto and is referred
to as the method of proxies here:
http://r-proto.googlecode.com/files/prototype_approaches.pdf

f <- function() x + y + z
f2 <- function(fun, ...) with(proto(environment(fun), ..., g = fun), g())
f2(f, x = 1, y = 2, z = 3)

The proto call creates an anonymous proto object whose parent is
the parent of fun.  The anonymous proto object contains the ...
arguments to f2 and g.    g is just fun with its environment reset to
the anonymous proto object. We then call g.



More information about the R-devel mailing list