41

我正在尝试从 R 中的 for 循环中填充数据框。列的名称是在循环中动态生成的,并且在填充数据框时将一些循环变量的值用作值。例如,当前列的名称可以是某个变量名称作为循环中的字符串,并且该列可以将当前迭代器的值作为其在数据框中的值。

我试图在循环外创建一个空数据框,就像这样

d = data.frame()

但我真的不能用它做任何事情,当我尝试填充它时,我遇到了一个错误

 d[1] = c(1,2)
Error in `[<-.data.frame`(`*tmp*`, 1, value = c(1, 2)) : 
  replacement has 2 rows, data has 0

什么可能是实现我想要做的事情的好方法。如果我不清楚,请告诉我。

4

6 回答 6

51

你可以这样做:

 iterations = 10
 variables = 2

 output <- matrix(ncol=variables, nrow=iterations)

 for(i in 1:iterations){
  output[i,] <- runif(2)

 }

 output

然后把它变成一个data.frame

 output <- data.frame(output)
 class(output)

这是做什么的:

  1. 根据预期增长创建具有行和列的矩阵
  2. 在矩阵中插入 2 个随机数
  3. 循环完成后将其转换为数据帧。
于 2012-11-18T17:30:57.040 回答
50

通常最好避免循环并使用矢量化函数。如果这不可能,有两种方法:

  1. 预先分配您的data.frame. 不建议这样做,因为data.frames.
  2. 在循环中使用另一个数据结构,然后转换为一个data.frame。Alist在这里非常有用。

举例说明一般方法:

mylist <- list() #create an empty list

for (i in 1:5) {
  vec <- numeric(5) #preallocate a numeric vector
  for (j in 1:5) { #fill the vector
    vec[j] <- i^j 
  }
  mylist[[i]] <- vec #put all vectors in the list
}
df <- do.call("rbind",mylist) #combine all vectors into a matrix

在此示例中,不必使用 a list,您可以预先分配 a matrix。但是,如果您不知道循环需要多少次迭代,您应该使用list.

最后,这里是示例循环的矢量化替代方案:

outer(1:5,1:5,function(i,j) i^j)

如您所见,它更简单,也更高效。

于 2012-11-18T17:32:40.310 回答
19

这也有效。

df = NULL
for (k in 1:10)
    {
       x = 1
       y = 2
       z = 3
       df = rbind(df, data.frame(x,y,z))
     }

输出看起来像这样

df #enter

x y z #col names
1 2 3
于 2018-10-10T19:58:33.930 回答
1

谢谢 Notable1,对我有用 tidytextr 创建一个数据框,其中一列中的文件名和另一列中的内容。

    diretorio <- "D:/base"
    arquivos <- list.files(diretorio, pattern = "*.PDF")
    quantidade <- length(arquivos)

#
df = NULL
for (k in 1:quantidade) {

      nome = arquivos[k]
      print(nome)
      Sys.sleep(1) 
      dados = read_pdf(arquivos[k],ocr = T)
      print(dados)
      Sys.sleep(1)
      df = rbind(df, data.frame(nome,dados))
      Sys.sleep(1)
}
Encoding(df$text) <- "UTF-8"
于 2019-07-31T20:18:47.703 回答
0

我有一个案例,我需要在 for 循环函数中使用数据框。在这种情况下,它是“高效的”,但是请记住,数据库很小,循环中的迭代非常简单。但也许该代码可能对具有类似条件的人有用。

for 循环的目的是沿五个位置(即 5 东京、纽约、圣保罗、苏尔和墨西哥城)使用栅格提取功能,每个位置都有各自的栅格网格。我有一个空间点数据库,在 5 个不同位置分配了 1000 多个观测值,我需要从 10 个不同的栅格网格(每个位置两个网格)中提取信息。此外,对于后续分析,我不仅需要栅格值,还需要每个观测值的唯一 ID。

准备好空间数据后,包括以下任务:

  1. 使用readOGR函数导入点 shapefile (rgdap 包)
  2. 使用光栅功能导入光栅文件(光栅包)
  3. 使用函数堆栈(光栅包)将同一位置的网格堆叠到一个文件中

这里使用数据框的for 循环代码:

1. 将每个位置的堆叠栅格添加到列表中

raslist <- list(LOC1,LOC2,LOC3,LOC4,LOC5)

2. 创建一个空数据框,这将是输出文件

TB <- data.frame(VAR1=double(),VAR2=double(),ID=character())

3.设置for循环功能

L1 <- seq(1,5,1) # the location ID is a numeric variable with values from 1 to 5 

for (i in 1:length(L1)) {
  dat=subset(points,LOCATION==i) # select corresponding points for location [i] 
  t=data.frame(extract(raslist[[i]],dat),dat$ID) # run extract function with points & raster stack for location [i]
  names(t)=c("VAR1","VAR2","ID") 
  TB=rbind(TB,t)
}
于 2017-08-24T17:08:27.677 回答
0

正在寻找相同的内容,以下内容也可能有用。

a <- vector("list", 1)
for(i in 1:3){a[[i]] <- data.frame(x= rnorm(2), y= runif(2))}
a
rbind(a[[1]], a[[2]], a[[3]]) 
于 2021-11-14T09:58:13.777 回答