Hi, It seems like the enclosed environment does not work well with the loop. Here is a simple example ``` FuncGenerator <- function(value){ function() message(value) } funcSets <- list() for(i in 1:2) funcSets[[i]] <- FuncGenerator(i) environment(funcSets[[1]])$value # [1] 2 environment(funcSets[[2]])$value # [1] 2 ``` The output from the last two lines is simply 2. I expect the first should be 1 and the second is 2. However, if I ask R to execute the message function before accessing its environment, the result is correct again. ``` FuncGenerator <- function(value){ function() message(value) } funcSets <- list() for(i in 1:2) funcSets[[i]] <- FuncGenerator(i) ## Ask to evaluate the function for(i in 1:2){ funcSets[[i]]() } # 1 # 2 environment(funcSets[[1]])$value # [1] 1 environment(funcSets[[2]])$value # [1] 2 ``` This does not make any sense to me since the function simply prints out its variable `value`. It should not change the value of the variable, so I think this might be a bug in the code optimizer. This issue can only be corrected by the loop(like the second example), manually evaluating the function without the loop will give you the same result as the first example. Here is my session information> sessionInfo()R version 4.1.2 (2021-11-01) Platform: x86_64-w64-mingw32/x64 (64-bit) Running under: Windows 10 x64 (build 19044) Best, Jiefei
Hi Jiefei, This is related to "lazy evaluation". Alternatives for dealing with it are discussed here: https://stackoverflow.com/questions/29084193/how-to-not-fall-into-rs-lazy-evaluation-trap HTH, Eric On Sun, Apr 3, 2022 at 6:32 AM Jiefei Wang <szwjf08 at gmail.com> wrote:> Hi, > > It seems like the enclosed environment does not work well with the > loop. Here is a simple example > ``` > FuncGenerator <- function(value){ > function() message(value) > } > > funcSets <- list() > for(i in 1:2) > funcSets[[i]] <- FuncGenerator(i) > > environment(funcSets[[1]])$value > # [1] 2 > environment(funcSets[[2]])$value > # [1] 2 > ``` > The output from the last two lines is simply 2. I expect the first > should be 1 and the second is 2. However, if I ask R to execute the > message function before accessing its environment, the result is > correct again. > > ``` > FuncGenerator <- function(value){ > function() message(value) > } > > funcSets <- list() > for(i in 1:2) > funcSets[[i]] <- FuncGenerator(i) > > ## Ask to evaluate the function > for(i in 1:2){ > funcSets[[i]]() > } > # 1 > # 2 > environment(funcSets[[1]])$value > # [1] 1 > environment(funcSets[[2]])$value > # [1] 2 > ``` > This does not make any sense to me since the function simply prints > out its variable `value`. It should not change the value of the > variable, so I think this might be a bug in the code optimizer. This > issue can only be corrected by the loop(like the second example), > manually evaluating the function without the loop will give you the > same result as the first example. > > Here is my session information > > sessionInfo() > R version 4.1.2 (2021-11-01) > Platform: x86_64-w64-mingw32/x64 (64-bit) > Running under: Windows 10 x64 (build 19044) > > > Best, > Jiefei > > ______________________________________________ > R-devel at r-project.org mailing list > https://stat.ethz.ch/mailman/listinfo/r-devel >[[alternative HTML version deleted]]
Hi Eric, Wow, Thanks for the explanation. Even though I know the lazy evaluation, I never thought it can have this surprising effect. Good to know it now. Best, Jiefei On Sun, Apr 3, 2022 at 12:20 AM Eric Berger <ericjberger at gmail.com> wrote:> > Hi Jiefei, > This is related to "lazy evaluation". Alternatives for dealing with it are discussed here: > > https://stackoverflow.com/questions/29084193/how-to-not-fall-into-rs-lazy-evaluation-trap > > HTH, > Eric > > > On Sun, Apr 3, 2022 at 6:32 AM Jiefei Wang <szwjf08 at gmail.com> wrote: >> >> Hi, >> >> It seems like the enclosed environment does not work well with the >> loop. Here is a simple example >> ``` >> FuncGenerator <- function(value){ >> function() message(value) >> } >> >> funcSets <- list() >> for(i in 1:2) >> funcSets[[i]] <- FuncGenerator(i) >> >> environment(funcSets[[1]])$value >> # [1] 2 >> environment(funcSets[[2]])$value >> # [1] 2 >> ``` >> The output from the last two lines is simply 2. I expect the first >> should be 1 and the second is 2. However, if I ask R to execute the >> message function before accessing its environment, the result is >> correct again. >> >> ``` >> FuncGenerator <- function(value){ >> function() message(value) >> } >> >> funcSets <- list() >> for(i in 1:2) >> funcSets[[i]] <- FuncGenerator(i) >> >> ## Ask to evaluate the function >> for(i in 1:2){ >> funcSets[[i]]() >> } >> # 1 >> # 2 >> environment(funcSets[[1]])$value >> # [1] 1 >> environment(funcSets[[2]])$value >> # [1] 2 >> ``` >> This does not make any sense to me since the function simply prints >> out its variable `value`. It should not change the value of the >> variable, so I think this might be a bug in the code optimizer. This >> issue can only be corrected by the loop(like the second example), >> manually evaluating the function without the loop will give you the >> same result as the first example. >> >> Here is my session information >> > sessionInfo() >> R version 4.1.2 (2021-11-01) >> Platform: x86_64-w64-mingw32/x64 (64-bit) >> Running under: Windows 10 x64 (build 19044) >> >> >> Best, >> Jiefei >> >> ______________________________________________ >> R-devel at r-project.org mailing list >> https://stat.ethz.ch/mailman/listinfo/r-devel