2017-06-27 34 views
0

我想使用函数'ggplot'将函数图分配给函数'eval'创建的对象。该对象位于一个循环中,因此定义为一个列表。在循环的每一轮中,应该使用变量'list_pos'将该图保存为列表的一个元素。错误'下标越界'使用eval() - 基于assign()的函数 - 循环中的函数

目标是创建三个不同的列表'Graphs_A','Graphs_B'和'Graphs_C',每个三个不同的图作为元素保存。因此,作为一个结果,我可以只运行

Graphs_A 

的R-代码如下所示调用特定亚群的地块,例如A组,在一次。在我的例子中,我总是将相同的图表分配给这些元素,当然,对于我的真实数据集,情况并非如此。

###### Example ##### 

# Load packages 

install.packages('ggplot2') 
library(ggplot2) 

# Creating data 

names <- c("A","B","C") 

numbers <- c(1,2,3) 

df <- data.frame(
    x = c(1, 2, 3, 4, 5, 6, 7, 8), 
    y = c(3, 2, 4, 4, 6, 8, 9, 8) 
) 

# Loop to assign ggplot to elements of list 

for(j in names){ 
    assign(paste("Graphs_", j, sep=""), list()) 
    list_pos <- 0 

    for(i in numbers){ 
     list_pos <- list_pos + 1 
     assign(
     eval(parse(text=paste("Graphs_", j, sep="")))[[list_pos]], 
     ggplot() + geom_point(data=df, aes(x=x, y=y)) # Plot depends in real data set on value of i 
    ) 
    } 
} 

我总是得到一个错误'下标越界'。我尝试了不同的东西,如重新定义列表

assign(paste("Graphs_", j, sep=""), list("X","Y","Z")) 

但它没有帮助将图分配给列表中的元素。我该如何处理这个问题?

+2

忘记存在'parse'和'assign'。除非你对R有更多的经验,否则你将不会得到有效的使用,他们只能让你编写糟糕的(效率低下,难以理解或维护)代码。 – Roland

+0

感谢您的回答。但不幸的是,我必须使用它们才能将值分配给我以前未创建的对象。因此,据我所知,这是创建一个嵌套循环的唯一方法,正如我在文章中提到的。 –

+0

你不必,你不应该。使用一个列表。 – Roland

回答

0

首先,行eval(parse(text=paste("Graphs_", j, sep="")))[[list_pos]]没有意义:parse(text=paste("Graphs_", j, sep=""))会产生一个字符串,eval会计算表达式。因此,你不能子集...

您可以eval(parse(text=...))工作,但我建议使用清单:

# Loop to assign ggplot to elements of list 
Graphs <- list() 
for(j in 1:length(names)){ 
    for(i in numbers){ 
     Graphs[[j]] <- ggplot() + geom_point(data=df, aes(x=x, y=y)) 
    } 
} 

我不知道你为什么要指定打印到列表中,但上面的代码运行...

+0

谢谢你的回答! 我已经考虑过你的解决方案。但它不适用于我,因为我想根据之前的循环回合将曲线保存在不同的对象'Graphs_'中。例如,对于第一轮'for(j in name)',我的实际数据集中的图是不同的,取决于循环的'for(i in numbers)'。因此,我希望根据'for(i in numbers)'得到三个列表'Graph_A','Graph_B'和'Graph_C',三个元素包含三个不同的图。因此,我可以一次为不同的小组分配地块。 –