在循环中分配和删除对象: eval(parse(paste(

发布于 2024-09-18 18:06:22 字数 627 浏览 8 评论 0原文

我正在寻找在循环中分配对象。我读过某种形式的 eval(parse() 是我执行此操作所需的,但我遇到了列出 无效文本no such 的错误文件或目录。下面是我通常尝试执行的操作的示例代码:

x <- array(seq(1,18,by=1),dim=c(3,2,3))
for (i in 1:length(x[1,1,])) {
  eval(parse(paste(letters[i],"<-mean(x[,,",i,"])",sep="")
}

当我使用完这些对象时,我想删除它们(实际对象非常大,稍后会导致内存问题on...)

for (i in 1:length(x[1,1,])) eval(parse(paste("rm(",letters[i],")",sep="")))

此脚本的两个 eval(parse(paste() 部分都会返回 无效文本没有此类文件或目录 的错误。Am我在使用 eval(parse() 时遗漏了一些东西?是否有更简单/更好的方法来在循环中分配对象?

I am looking to assign objects in a loop. I've read that some form of eval(parse( is what I need to perform this, but I'm running into errors listing invalid text or no such file or directory. Below is sample code of generally what I'm attempting to do:

x <- array(seq(1,18,by=1),dim=c(3,2,3))
for (i in 1:length(x[1,1,])) {
  eval(parse(paste(letters[i],"<-mean(x[,,",i,"])",sep="")
}

And when I'm finished using these objects, I would like to remove them (the actual objects are very large and cause memory problems later on...)

for (i in 1:length(x[1,1,])) eval(parse(paste("rm(",letters[i],")",sep="")))

Both eval(parse(paste( portions of this script return errors for invalid text or no such file or directory. Am I missing something in using eval(parse(? Is there a easier/better way to assign objects in a loop?

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

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

发布评论

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

评论(4

や三分注定 2024-09-25 18:06:22

这是一种非常令人厌恶和令人沮丧的处理方式。使用assign 进行分配,使用rm 的列表参数来删除对象。

> for (i in 1:length(x[1,1,])) {
+   assign(letters[i],mean(x[,,i]))
+ }
> ls()
[1] "a" "b" "c" "i" "x"
> a
[1] 3.5
> b
[1] 9.5
> c
[1] 15.5
> for (i in 1:length(x[1,1,])) {
+   rm(list=letters[i])
+ }
> ls()
[1] "i" "x"
> 

每当您觉得需要使用 parse 时,请记住 Fortune(106):

如果答案是 parse() 你应该
通常会重新思考这个问题。
-- Thomas Lumley,R-help(2005 年 2 月)

That's a pretty disgusting and frustrating way to go about it. Use assign to assign and rm's list argument to remove objects.

> for (i in 1:length(x[1,1,])) {
+   assign(letters[i],mean(x[,,i]))
+ }
> ls()
[1] "a" "b" "c" "i" "x"
> a
[1] 3.5
> b
[1] 9.5
> c
[1] 15.5
> for (i in 1:length(x[1,1,])) {
+   rm(list=letters[i])
+ }
> ls()
[1] "i" "x"
> 

Whenever you feel the need to use parse, remember fortune(106):

If the answer is parse() you should
usually rethink the question.
-- Thomas Lumley, R-help (February 2005)

何其悲哀 2024-09-25 18:06:22

尽管似乎有更好的方法来处理这个问题,但如果您真的确实想要使用“eval(parse(paste(”)方法,那么您缺少的是文本标志。parse

假设它的第一个参数是一个文件的路径,然后将对其进行解析,在您的情况下,您不希望它去读取要解析的文件,您希望直接向其传递一些要解析的文本。因此,重写的代码(以上面所谓的令人厌恶的形式)

letters=c('a','b','c')
x <- array(seq(1,18,by=1),dim=c(3,2,3))
for (i in 1:length(x[1,1,])) {
  eval(parse(text=paste(letters[i],"<-mean(x[,,",i,"])",sep="")))
}

除了不指定“text =”之外,还缺少右侧的一些括号来关闭解析和评估语句,

这听起来像您的 。问题已经解决了,但是对于到达此页面的人来说,他们确实想使用 eval(parse(paste,我想澄清一下。

Although it seems there are better ways to handle this, if you really did want to use the "eval(parse(paste(" approach, what you're missing is the text flag.

parse assumes that its first argument is a path to a file which it will then parse. In your case, you don't want it to go reading a file to parse, you want to directly pass it some text to parse. So, your code, rewritten (in what has been called disgusting form above) would be

letters=c('a','b','c')
x <- array(seq(1,18,by=1),dim=c(3,2,3))
for (i in 1:length(x[1,1,])) {
  eval(parse(text=paste(letters[i],"<-mean(x[,,",i,"])",sep="")))
}

In addition to not specifying "text=" you're missing a few parentheses on the right side to close your parse and eval statements.

It sounds like your problem has been solved, but for people who reach this page who really do want to use eval(parse(paste, I wanted to clarify.

故事↓在人 2024-09-25 18:06:22

非常糟糕的主意;你永远不应该在 R 中使用 evalparse,除非你完全知道自己在做什么。
可以使用以下方式创建变量:

name<-"x"
assign(name,3) #Eqiv to x<-3

并通过以下方式删除:

name<-"x"
rm(list=name)

但在您的情况下,可以使用简单的命名向量来完成:

apply(x,3,mean)->v;names(v)<-letters[1:length(v)]
v
v["b"]
#Some operations on v
rm(v)

Very bad idea; you should never use eval or parse in R, unless you perfectly know what you are doing.
Variables can be created using:

name<-"x"
assign(name,3) #Eqiv to x<-3

And removed by:

name<-"x"
rm(list=name)

But in your case, it can be done with simple named vector:

apply(x,3,mean)->v;names(v)<-letters[1:length(v)]
v
v["b"]
#Some operations on v
rm(v)
清晨说晚安 2024-09-25 18:06:22

在这种情况下,最好避免使用 eval(paste( 或 allocate )。这样做会创建许多全局变量,这些变量只会在以后引起额外的麻烦。

最好的方法是使用现有的数据结构来存储对象,列表是最通用的对于这些类型的情况,

您可以使用 [ls]apply 函数来处理不同的元素,通常比循环全局变量要快得多。如果您想保存创建的所有对象,则只需保存一个列表。当需要删除它们时,您只需删除 1 个单个对象,所有内容都会消失(无需循环),您可以命名列表中的元素,以便稍后通过名称或索引来引用它们。

It is best to avoid using either eval(paste( or assign in this case. Doing either creates many global variables that just cause additional headaches later on.

The best approach is to use existing data structures to store your objects, lists are the most general for these types of cases.

Then you can use the [ls]apply functions to do things with the different elements, usually much quicker than looping through global variables. If you want to save all the objects created, you have just one list to save/load. When it comes time to delete them, you just delete 1 single object and everything is gone (no looping). You can name the elements of the list to refer to them by name later on, or by index.

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