已经有很多关于范围、环境和功能的讨论。参见例如here https://stackoverflow.com/questions/23234640/why-do-variable-lookups-in-the-body-of-function-a-take-values-from-the-global-en/23296536#23296536 or here https://stackoverflow.com/questions/2646402/using-functions-and-environments。但是,我不确定是否找到了解决以下问题的好方法:
df <- data.frame(id=rep(LETTERS[1:2],each=2), x=1:4)
d <- -1
myfun <- function(df, d){
require(plyr)
new.dat <- ddply(df, .(id), transform, x=x*d)
return(new.dat)}
myfun(df, 1)
您可以轻松验证全局定义的d=-1
被使用,而不是d=1
正如论证中所提供的。 (如果没有全局定义d
存在,那么有一个object not found
消息已返回)现在最大的问题是:我该如何制作d
使用函数的参数而不是全局定义的参数d
?
我的印象是以下应该有效:
myfun2 <- function(df, d){
here <- environment()
new.dat <- ddply(df, .(id), transform, x=x*with(here,d))
return(new.dat)}
myfun2(df, 1)
据我了解with(here, d)
检索对象d
来自环境here
。所以,结果应该是1
。但会返回一个错误,指出
Error in eval(substitute(expr), data, enclos = parent.frame()) :
invalid 'envir' argument of type 'closure'
我不确定我是否理解为什么这行不通,如果有人能够阐明这一点,或者您可以提供替代解决方案,我会很高兴。注意包裹整个ddply
- 语句进入with(...)
似乎也没有帮助。
一个有效的解决方案是attach
函数内的当前环境:
myfun3 <- function(df, d){
here <- environment()
attach(here)
new.dat <- ddply(df, .(id), transform, x=x*d)
detach(here)
return(new.dat)
}
但我不喜欢这个解决方案,因为它通过屏蔽全局定义来工作d
与当地d
,我认为这不是很优雅。
任何意见/指示表示赞赏。