标题是一个独立的问题。一个例子澄清了它:考虑
x=list(a=1, b="name")
f <- function(){
assign('y[["d"]]', FALSE, parent.frame() )
}
g <- function(y) {f(); print(y)}
g(x)
$a
[1] 1
$b
[1] "name"
而我想得到
g(x)
$a
[1] 1
$b
[1] "name"
$d
[1] FALSE
一些评论。我知道我的原始例子中有什么问题,但我用它来明确我的目标。我想避免&lt;&lt; - ,并希望在父框架中更改x。
我认为我对环境的理解是原始的,任何引用都会受到赞赏。
答案 0 :(得分:6)
assign
的第一个参数必须是变量名,而不是表达式的字符表示。尝试将f
替换为:
f <- function() with(parent.frame(), y$d <- FALSE)
请注意,a
,b
和d
是列表组件,而不是列表属性。如果我们想在"d"
的父框架中向y
添加属性f
,我们会这样做:
f <- function() with(parent.frame(), attr(y, "d") <- FALSE)
另外,请注意,根据您想要做的事情,将x
作为环境或proto对象(来自proto包)可能(或可能不)更好。
答案 1 :(得分:3)
assign
的第一个参数需要是一个对象名称。您对assign
的使用与分配帮助页面末尾的计数器示例基本相同。观察:
> x=list(a=1, b="name")
> f <- function(){
+ assign('x["d"]', FALSE, parent.frame() )
+ }
> g <- function(y) {f(); print(`x["d"]`)}
> g(x)
[1] FALSE # a variable with the name `x["d"]` was created
这可能是您想要使用“&lt;&lt; - ”的地方,但通常被认为是可疑的。
> f <- function(){
+ x$d <<- FALSE
+ }
> g <- function(y) {f(); print(y)}
> g(x)
$a
[1] 1
$b
[1] "name"
$d
[1] FALSE
进一步的想法是,在没有任何目标进行这项练习而忽略了Gabor指出的“属性”一词在R中具有特定含义,但可能不是你的目标。如果你想要的只是符合你的规格的输出,那么这就达到了这个目标,但注意到全球环境中没有发生x的变化。
> f <- function(){
+ assign('y', c(x, d=FALSE), parent.frame() )
+ }
> g <- function(y) {f(); print(y)}
> g(x)
$a
[1] 1
$b
[1] "name"
$d
[1] FALSE
> x # `x` is unchanged
$a
[1] 1
$b
[1] "name"
f
的parent.frame可称为“g
的内部”,但更改不会传播到全局环境。