Reputation: 2540
I have a bunch of data frames generated by:
for(i in 1:100){
assign(paste("df", i, sep=""), data.frame(1,2))
}
I want to rename the first column of all of these 100 data frames to be Column1
. (Note that in my real data each first column is unique, unlike the example here, where they are each X1
.) This will be the same for all data frames.
For any individual one, I can do this. For example:
names(df45)[1]<-"Column1"
However, I am running into problems when attempting to automate the process. Here is the (wrong) code I have tried:
names(eval(parse(text=paste("df", i, sep=""))))[1] <- "Column1"
How should I modify this? And is there a quicker way to access variables in loops that this?
I have come across other answers that say it is better to put these things in a list and process it like this:
#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"
}
However, I want to be able to merge all the data frames together as follows:
df <- merge(df1, df2, df3, df4, ....... df100, by="Column1")
Upvotes: 2
Views: 3896
Reputation: 70653
First of all, I would work on a list (of data.frames). You can use lapply to "climb" each list element. I'm borrowing the merge approach from @baptiste (posted in comments).
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
Upvotes: 4
Reputation: 640
Maybe this works for you
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)
Upvotes: 1