我有一个数据帧列表:
set.seed(23)
date_list = seq(1:30)
testframe = data.frame(Date = date_list)
testframe$ABC = rnorm(30)
testframe$DEF = rnorm(30)
testframe$GHI = seq(from = 10, to = 25, length.out = 30)
testframe$JKL = seq(from = 5, to = 45, length.out = 30)
testlist = list(testframe, testframe, testframe)
names(testlist) = c("df1464", "df6355", "df94566")
我现在想提取每个数据框的名称并将其添加到其列中。因此,列表中第一个数据框的列名应为:Date_df1464, ABC_df1464, DEF_df1464, GHI_df1464 and JKL_df1464
我创建了这个循环,但是它不起作用:
for (a in names(testlist)) {
for(i in 1: length(testlist)){
allcolnames = colnames(testlist[[i]])
allcolnames = paste(allcolnames, a , sep = "_")
testlist[[i]] = colnames(allcolnames)
}
}
我收到此错误:
Error in testlist[[i]] : subscript out of bounds
我很不知道为什么它不起作用。有什么想法吗?
答案 0 :(得分:2)
您可以依次切换两个Map
;内部Map
准备新名称,外部Map
将其应用于子列表的名称。
testlist <- Map(`names<-`, testlist,
Map(paste, lapply(testlist, names), names(testlist), sep="_"))
结果
lapply(testlist, names)
# $df1464
# [1] "Date_df1464" "ABC_df1464" "DEF_df1464" "GHI_df1464" "JKL_df1464"
#
# $df6355
# [1] "Date_df6355" "ABC_df6355" "DEF_df6355" "GHI_df6355" "JKL_df6355"
#
# $df94566
# [1] "Date_df94566" "ABC_df94566" "DEF_df94566" "GHI_df94566" "JKL_df94566"
答案 1 :(得分:2)
两种方法可以做到这一点。更好,更封装的方法是使用Map
,循环遍历各个数据帧及其对应的名称:
new.testlist <- Map(function(df, name) {
names(df) <- paste(names(df), name, sep = '_')
return(df)
}, testlist, names(testlist))
> str(new.testlist)
List of 3
$ df1464 :'data.frame': 30 obs. of 5 variables:
..$ Date_df1464: int [1:30] 1 2 3 4 5 6 7 8 9 10 ...
..$ ABC_df1464 : num [1:30] 0.193 -0.435 0.913 1.793 0.997 ...
..$ DEF_df1464 : num [1:30] -0.5532 0.0982 -1.1467 -1.2499 -0.2021 ...
..$ GHI_df1464 : num [1:30] 10 10.5 11 11.6 12.1 ...
..$ JKL_df1464 : num [1:30] 5 6.38 7.76 9.14 10.52 ...
$ df6355 :'data.frame': 30 obs. of 5 variables:
..$ Date_df6355: int [1:30] 1 2 3 4 5 6 7 8 9 10 ...
..$ ABC_df6355 : num [1:30] 0.193 -0.435 0.913 1.793 0.997 ...
..$ DEF_df6355 : num [1:30] -0.5532 0.0982 -1.1467 -1.2499 -0.2021 ...
..$ GHI_df6355 : num [1:30] 10 10.5 11 11.6 12.1 ...
..$ JKL_df6355 : num [1:30] 5 6.38 7.76 9.14 10.52 ...
$ df94566:'data.frame': 30 obs. of 5 variables:
..$ Date_df94566: int [1:30] 1 2 3 4 5 6 7 8 9 10 ...
..$ ABC_df94566 : num [1:30] 0.193 -0.435 0.913 1.793 0.997 ...
..$ DEF_df94566 : num [1:30] -0.5532 0.0982 -1.1467 -1.2499 -0.2021 ...
..$ GHI_df94566 : num [1:30] 10 10.5 11 11.6 12.1 ...
..$ JKL_df94566 : num [1:30] 5 6.38 7.76 9.14 10.52 ...
风险更大的方法是使用超级赋值运算符来遍历名称,并相信testlist
在您的全局环境中仍然可靠。请注意,第二种方法会更改testlist
中的列名,这是一个副作用,通常不认为是好的做法。 Max Teflon的答案有些相似,因为它依赖于全局环境中存在的testlist
,而没有将其显式传递给修改函数。
sapply(names(testlist), function(x) {
names(testlist[[x]]) <<- paste(names(testlist[[x]]), x, sep = '_')
})
答案 2 :(得分:1)
您的解决方案几乎是正确的,您只需要循环两次即可。
而您的colnames
通话是错误的方法。
这应该起作用:
for(i in 1: length(testlist)){
allcolnames = colnames(testlist[[i]])
allcolnames = paste(allcolnames, names(testlist)[i] , sep = "_")
colnames(testlist[[i]]) = allcolnames
}
这也可以,没有任何缺点;):
set.seed(23)
date_list = seq(1:30)
testframe = data.frame(Date = date_list)
testframe$ABC = rnorm(30)
testframe$DEF = rnorm(30)
testframe$GHI = seq(from = 10, to = 25, length.out = 30)
testframe$JKL = seq(from = 5, to = 45, length.out = 30)
testlist = list(testframe, testframe, testframe)
names(testlist) = c("df1464", "df6355", "df94566")
out <- lapply(names(testlist),function(name){
dummy <- testlist[[name]]
names(dummy) <- paste0(names(testlist[[name]]) ,'_',name)
dummy
})
str(out)
#> List of 3
#> $ :'data.frame': 30 obs. of 5 variables:
#> ..$ Date_df1464: int [1:30] 1 2 3 4 5 6 7 8 9 10 ...
#> ..$ ABC_df1464 : num [1:30] 0.193 -0.435 0.913 1.793 0.997 ...
#> ..$ DEF_df1464 : num [1:30] -0.5532 0.0982 -1.1467 -1.2499 -0.2021 ...
#> ..$ GHI_df1464 : num [1:30] 10 10.5 11 11.6 12.1 ...
#> ..$ JKL_df1464 : num [1:30] 5 6.38 7.76 9.14 10.52 ...
#> $ :'data.frame': 30 obs. of 5 variables:
#> ..$ Date_df6355: int [1:30] 1 2 3 4 5 6 7 8 9 10 ...
#> ..$ ABC_df6355 : num [1:30] 0.193 -0.435 0.913 1.793 0.997 ...
#> ..$ DEF_df6355 : num [1:30] -0.5532 0.0982 -1.1467 -1.2499 -0.2021 ...
#> ..$ GHI_df6355 : num [1:30] 10 10.5 11 11.6 12.1 ...
#> ..$ JKL_df6355 : num [1:30] 5 6.38 7.76 9.14 10.52 ...
#> $ :'data.frame': 30 obs. of 5 variables:
#> ..$ Date_df94566: int [1:30] 1 2 3 4 5 6 7 8 9 10 ...
#> ..$ ABC_df94566 : num [1:30] 0.193 -0.435 0.913 1.793 0.997 ...
#> ..$ DEF_df94566 : num [1:30] -0.5532 0.0982 -1.1467 -1.2499 -0.2021 ...
#> ..$ GHI_df94566 : num [1:30] 10 10.5 11 11.6 12.1 ...
#> ..$ JKL_df94566 : num [1:30] 5 6.38 7.76 9.14 10.52 ...