【问题标题】:Change column names of many data frames in a for-loop在 for 循环中更改许多数据框的列名
【发布时间】:2014-11-13 21:41:58
【问题描述】:

我有一堆数据帧生成:

for(i in 1:100){
    assign(paste("df", i, sep=""), data.frame(1,2))
}

我想将所有这 100 个数据框的第一列重命名为 Column1。 (请注意,在我的真实数据中,每一列都是唯一的,与此处的示例不同,它们都是 X1。)这对于所有数据帧都是相同的。

对于任何个人,我都可以做到。例如:

names(df45)[1]<-"Column1"

但是,我在尝试自动化该过程时遇到了问题。这是我尝试过的(错误的)代码:

names(eval(parse(text=paste("df", i, sep=""))))[1] <- "Column1"

我应该如何修改这个?有没有比这个更快的方法来访问循环中的变量?

我遇到过其他答案说最好将这些东西放在一个列表中并像这样处理它:

#put into a list
l.df <- lapply(ls(pattern="df[0-9]+"), function(x) get(x))

for(i in 1:100){
    names(l.df[[i]])[1] <- "Column1"
}

但是,我希望能够将所有数据框合并在一起,如下所示:

df <- merge(df1, df2, df3, df4, ....... df100, by="Column1")

【问题讨论】:

  • 请将数据框放在一个列表中,而不是将它们创建为单独的命名对象。这使得列的重命名和merge 操作变得无限容易(因为无论数据帧的数量如何,相同的代码都可以工作)。
  • @baptiste,假设我已将列名全部更改为 Column1。我不太清楚do.call 部分。我试过这个:do.call("merge", c(l.df, by="Column1")).
  • 如果合并允许超过 2 个 data.frames 作为参数,那将会起作用。在这里你可以使用Reduce(function(x,y)merge(x,y,by="Column1"), l.df)
  • 很高兴知道。谢谢!

标签: r variables assign


【解决方案1】:

首先,我会处理一个(data.frames)列表。您可以使用 lapply 来“爬升”每个列表元素。我借用了@baptiste 的合并方法(发布在 cmets 中)。

xy <- replicate(10, data.frame(a = 1:10, b = runif(10)), simplify = FALSE)
xy <- lapply(xy, function(x) {names(x)[1] <- "Golum1"; x})
Reduce(function(x,y) merge(x,y,by="Golum1"), xy)

   Golum1          b.x        b.y        b.x        b.y       b.x        b.y       b.x       b.y        b.x        b.y
1       1 0.0002497286 0.44790338 0.12656118 0.85306085 0.9502253 0.92816557 0.6727456 0.3615492 0.71520420 0.26933313
2       2 0.1416911036 0.56330792 0.03834924 0.95777112 0.4763716 0.28533075 0.8729803 0.7035205 0.49824660 0.15685903
3       3 0.3454216446 0.42778131 0.35065726 0.35513107 0.6610847 0.21600874 0.9611296 0.2527102 0.62142047 0.32401890
4       4 0.2128049061 0.20300980 0.35529195 0.19681124 0.6105881 0.85292309 0.3311055 0.4953804 0.05079081 0.98322541
5       5 0.5967234119 0.93926727 0.74456886 0.25971581 0.3739592 0.01498909 0.2683361 0.9895955 0.45829244 0.76854781
6       6 0.4843087369 0.04535037 0.29100912 0.05801034 0.1010084 0.31980135 0.7572697 0.6022717 0.86408382 0.10516840
7       7 0.0624480459 0.58510411 0.62256365 0.97236759 0.6910560 0.21823825 0.8169870 0.3162987 0.79414611 0.43907780
8       8 0.1764713391 0.05768646 0.30316764 0.25180931 0.9378119 0.06416274 0.6814944 0.9889381 0.13944101 0.51939788
9       9 0.9533833019 0.70950657 0.04435285 0.92314396 0.4208451 0.34137729 0.8876309 0.9789025 0.43711122 0.71978702
10     10 0.7814107563 0.93566272 0.76036172 0.71139862 0.5308587 0.19734855 0.8359664 0.6903358 0.22433803 0.09343658

# warnings are due to name collisions

【讨论】:

    【解决方案2】:

    也许这对你有用

     for(i in 1:100){
      assign(paste("df", i, sep=""), data.frame(1,2))
    }
    
    require(naturalsort)
    data<-do.call(rbind,sapply(ls(pattern="df[0-9]+"),function(x) get(x),simplify = F))
    data<-data[naturalorder(rownames(data)),]
    
    colnames(data)[1] <-'Column1'
    
    head(data)
    

    【讨论】:

      猜你喜欢
      • 1970-01-01
      • 1970-01-01
      • 2020-09-19
      • 1970-01-01
      • 2019-08-20
      • 1970-01-01
      • 1970-01-01
      • 2016-05-07
      • 1970-01-01
      相关资源
      最近更新 更多