如何使用R自动重命名宽数据中的列
以宽幅格式考虑以下数据如何使用R自动重命名宽数据中的列,r,dataframe,rename,mutate,R,Dataframe,Rename,Mutate,以宽幅格式考虑以下数据 df<-data.frame("id"=c(1,2,3,4), "ex"=c(1,0,0,1), "aQL"=c(5,4,NA,6), "bQL"=c(5,7,NA,9), "cQL"=c(5,7,NA,9), "bST"=c(3,7,8,
df<-data.frame("id"=c(1,2,3,4),
"ex"=c(1,0,0,1),
"aQL"=c(5,4,NA,6),
"bQL"=c(5,7,NA,9),
"cQL"=c(5,7,NA,9),
"bST"=c(3,7,8,9),
"cST"=c(8,7,5,3),
"aXY"=c(1,9,4,4),
"cXY"=c(5,3,1,4))
主数据集有许多变量,因此我希望重命名以自动方式完成。我尝试了以下代码
renameCol <- function(x) {
setNames(x, paste0("QL.", seq_len(ncol(x))))
}
renameCol(df)
renameCol这是一个通过stringr
包使用正则表达式的解决方案:
库(stringr)
df我建议一种不需要函数的tidyverse
方法。在此解决方案中,您可以提取每个变量名称的第一个字母作为id,然后使用cur\u group\u id
分配一个数字,以便保持顺序。最后,使用这个新数字转换包含名称的变量,然后格式化为wide,以获得预期的输出:
library(tidyverse)
#Data
df<-data.frame("id"=c(1,2,3,4),
"ex"=c(1,0,0,1),
"aQL"=c(5,4,NA,6),
"bQL"=c(5,7,NA,9),
"cQL"=c(5,7,NA,9),
"bST"=c(3,7,8,9),
"cST"=c(8,7,5,3),
"aXY"=c(1,9,4,4),
"cXY"=c(5,3,1,4))
#Reshape
df %>% pivot_longer(cols = -c(1,2)) %>%
#Extract first letter as id
mutate(id2=substring(name,1,1)) %>%
#Create the number id
group_by(id2) %>%
mutate(id3=cur_group_id()) %>%
#Clean name
mutate(name=substring(name,2,nchar(name))) %>%
#Create final var
mutate(name2=paste0(name,'.',id3)) %>% ungroup() %>%
dplyr::select(-c(name,id2,id3)) %>%
#Format to wide
pivot_wider(names_from = name2,values_from=value)
库(tidyverse)
#资料
df%pivot_更长(cols=-c(1,2))%>%
#提取第一个字母作为id
突变(id2=子字符串(名称,1,1))%>%
#创建数字标识
分组依据(id2)%>%
突变(id3=cur_group_id())%>%
#干净的名字
突变(名称=子字符串(名称,2,nchar(名称)))%>%
#创建最终变量
mutate(name2=paste0(name,'.',id3))%%>%ungroup()%%>%
dplyr::select(-c(名称,id2,id3))%>%
#格式要宽
枢轴(名称从=name2,值从=value)
输出:
# A tibble: 4 x 9
id ex QL.1 QL.2 QL.3 ST.2 ST.3 XY.1 XY.3
<dbl> <dbl> <dbl> <dbl> <dbl> <dbl> <dbl> <dbl> <dbl>
1 1 1 5 5 5 3 8 1 5
2 2 0 4 7 7 7 7 9 3
3 3 0 NA NA NA 8 5 4 1
4 4 1 6 9 9 9 3 4 4
#一个tible:4 x 9
id ex QL.1 QL.2 QL.3 ST.2 ST.3 XY.1 XY.3
1 1 1 5 5 5 3 8 1 5
2 2 0 4 7 7 7 7 9 3
3 3 0 NA NA 8 5 4 1
4 4 1 6 9 9 9 3 4 4
您可以尝试的另一种方法
colnames(df)[grepl("QL", colnames(df))] <- str_c("QL.", 1:3)
colnames(df)[grepl("ST", colnames(df))] <- str_c("ST.", 2:3)
colnames(df)[grepl("XY", colnames(df))] <- str_c("XY.", c(1,3))
# id ex QL.1 QL.2 QL.3 ST.2 ST.3 XY.1 XY.3
# 1 1 1 5 5 5 3 8 1 5
# 2 2 0 4 7 7 7 7 9 3
# 3 3 0 NA NA NA 8 5 4 1
# 4 4 1 6 9 9 9 3 4 4
colnames(df)[grepl(“QL”,colnames(df))]使用基本模式匹配:
您需要定义一个函数,该函数在单个列名上执行所需的操作:
f = function(x){
beg <- str_extract(x,"[a-z](?=[A-Z]{2})")
num <- which(letters == beg)
output <- paste0(str_extract(x,"(?<=[a-z])[A-Z]{2}"),".",num)
return(output)
}
然后,您可以直接在数据帧的名称上使用regmatches
和正则表达式:
m <- gregexpr("[a-z][A-Z]{2}", names(df),perl = T)
regmatches(names(df), m) <- lapply(regmatches(names(df), m), f)
names(df)
> names(df)
[1] "id" "ex" "QL.1" "QL.2" "QL.3" "ST.2" "ST.3" "XY.1" "XY.3"
m在基本R中,您可以执行以下操作:
names(df) <- sub("(\\d)([A-Z]{2})$","\\2.\\1", chartr("abc","123",names(df)))
df
id ex QL.1 QL.2 QL.3 ST.2 ST.3 XY.1 XY.3
1 1 1 5 5 5 3 8 1 5
2 2 0 4 7 7 7 7 9 3
3 3 0 NA NA NA 8 5 4 1
4 4 1 6 9 9 9 3 4 4
names(df)谢谢!这里有些秩序。变量的前缀a、b、c的顺序为.1、.2、.3。是否可以将“bST”和“cXY”重新编码为ST.2和XY.3?谢谢!你能解释一下改名的工作原理吗?e、 g.如果你考虑改名为a.QL、b.QL、c.QL、a.ST、e.t.c.@TRichard这里发生的事情是chartr
将abc
更改为123
等尝试chartr(“abcde”,“12345”,“你是我的国王”)
你会注意到aeiou
已分别更改为12345
。然后使用sub
捕获一个\\d
(数字),后跟[a-Z]{2}
2个大写字母,并在两个组之间放置一个点,同时切换捕获组的顺序。即尝试执行sub(\\d)([a-Z]{2}),“\\2-\\1”,“2DR”)
m <- gregexpr("[a-z][A-Z]{2}", names(df),perl = T)
regmatches(names(df), m) <- lapply(regmatches(names(df), m), f)
names(df)
> names(df)
[1] "id" "ex" "QL.1" "QL.2" "QL.3" "ST.2" "ST.3" "XY.1" "XY.3"
names(df) <- sub("(\\d)([A-Z]{2})$","\\2.\\1", chartr("abc","123",names(df)))
df
id ex QL.1 QL.2 QL.3 ST.2 ST.3 XY.1 XY.3
1 1 1 5 5 5 3 8 1 5
2 2 0 4 7 7 7 7 9 3
3 3 0 NA NA NA 8 5 4 1
4 4 1 6 9 9 9 3 4 4
names(df) <- sub("(\\d)([A-Z]{2})$","\\2.\\1", chartr("abc","123",names(df)))
a <- read.table(text=grep("\\.\\d",names(df),value = TRUE), sep=".")
b <- subset(aggregate(.~V1, a, function(x) setdiff(1:3,x)), V2>0)
df[do.call(paste, c(sep = ".", b))] <- NA
(df1 <- df[c(1, 2, order(names(df)[-(1:2)]) + 2)])
id ex QL.1 QL.2 QL.3 ST.1 ST.2 ST.3 XY.1 XY.2 XY.3
1 1 1 5 5 5 NA 3 8 1 NA 5
2 2 0 4 7 7 NA 7 7 9 NA 3
3 3 0 NA NA NA NA 8 5 4 NA 1
4 4 1 6 9 9 NA 9 3 4 NA 4