在环境中分配列表属性

发布于 2024-11-24 10:36:40 字数 409 浏览 2 评论 0原文

标题是一个独立的问题。一个例子可以澄清这一点:考虑一下

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

一些评论。我知道我原来的例子有什么问题,但我用它来明确我的目标。我想避免 <<-,并希望 x 在父框架中更改。

我认为我对环境的理解很原始,任何参考资料都会受到赞赏。

The title is the self-contained question. An example clarifies it: Consider

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"

whereas I would like to get

g(x)

$a
[1] 1

$b
[1] "name"

$d
[1] FALSE

A few remarks. I knew what is wrong in my original example, but am using it to make clear my objective. I want to avoid <<-, and want x to be changed in the parent frame.

I think my understanding of environments is primitive, and any references are appreciated.

如果你对这篇内容有疑问,欢迎到本站社区发帖提问 参与讨论,获取更多帮助,或者扫码二维码加入 Web 技术交流群。

扫码二维码加入Web技术交流群

发布评论

需要 登录 才能够评论, 你可以免费 注册 一个本站的账号。

评论(2

握住你手 2024-12-01 10:36:40

assign 的第一个参数必须是变量名,而不是表达式的字符表示形式。尝试将 f 替换为:

f <- function() with(parent.frame(), y$d <- FALSE)

请注意,abd 是列表组件,而不是列表属性。如果我们想在 f 的父框架中向 y 添加属性 "d",我们会这样做:

f <- function() with(parent.frame(), attr(y, "d") <- FALSE)

另外,请注意,取决于你想要做什么,让 x 成为一个环境或一个 proto 对象(来自 proto 包)可能会(也可能不会)更好。

The first argument to assign must be a variable name, not the character representation of an expression. Try replacing f with:

f <- function() with(parent.frame(), y$d <- FALSE)

Note that a, b and d are list components, not list attributes. If we wanted to add an attribute "d" to y in f's parent frame we would do this:

f <- function() with(parent.frame(), attr(y, "d") <- FALSE)

Also, note that depending on what you want to do it may (or may not) be better to have x be an environment or a proto object (from the proto package).

人生戏 2024-12-01 10:36:40

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

这可能是您想要使用“<<-”的地方,但它通常被认为是可疑的。

> 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 的内部”,但更改不会传播到全局环境。

assign's first argument needs to be an object name. Your use of assign is basically the same as the counter-example at the end of the the assign help page. Observe:

> 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

This may be where you want to use "<<-" but it's generally considered suspect.

> f <- function(){
+     x$d <<- FALSE
+ }
> g <- function(y) {f(); print(y)}
> g(x)
$a
[1] 1

$b
[1] "name"

$d
[1] FALSE

A further thought, offered in the absence of any goal for this exercise and ignoring the term "attributes" which Gabor has pointed out has a specific meaning in R, but may not have been your goal. If all you want is the output to match your specs then this achieves that goal but take notice that no alteration of x in the global environment is occurring.

> 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"

The parent.frame for f is what might be called the "interior of g but the alteration does not propagate out to the global environment.

~没有更多了~
我们使用 Cookies 和其他技术来定制您的体验包括您的登录状态等。通过阅读我们的 隐私政策 了解更多相关信息。 单击 接受 或继续使用网站,即表示您同意使用 Cookies 和您的相关数据。
原文