如何利用主data.frame批量修改列表中各data.frame的行名?
问题:利用主data.frame批量修改列表中多个data.frame的行名
我有一个由多个data.frame组成的列表,想要通过一个主data.frame来统一修改这些data.frame的行名。
示例数据
列表数据:
df <- data.frame(Value = c(1, 0, 6, 3, 4)) rownames(df) <- c("B144","B211","B678","B111", "B7090") df2 <- data.frame(Value = c(0, 0, 1, 4, 2)) rownames(df2) <- c("V2","V543","V6577","V4322", "V55") List <- list(df, df2)
主data.frame:
master = data.frame(ID=c("B144", "B211", "B7090","B111", "B678", "B242", "V4322", "V2694", "V4399", "V543","V6577","V2", "V55", "V554", "V2009"), rename=c("S1","S2", "S3","N1","N2","S4","S5","N3","N4","N5","S6","S7","S8", "N6", "N7"))
期望输出
修改后的列表中,每个data.frame的行名替换为主data.frame中对应ID的rename值:
df <- data.frame(Value = c(1, 0, 6, 3, 4)) rownames(df) <- c("S1","S2","N2","N1", "S3") df2 <- data.frame(Value = c(0, 0, 1, 4, 2)) rownames(df2) <- c("S7","N5","S6","S5", "S8") List <- list(df, df2)
解决方案
核心逻辑是将主表转换为ID-新行名的映射关系,再批量替换列表中每个data.frame的行名,以下是两种常用实现方式:
方法1:基础循环(无需额外包)
先把主data.frame转换成命名向量提升匹配效率,再遍历列表修改行名:
# 将主表转为命名向量:名字为原ID,值为新行名 name_map <- setNames(master$rename, master$ID) # 遍历列表逐个修改行名 for (i in seq_along(List)) { new_rownames <- name_map[rownames(List[[i]])] rownames(List[[i]]) <- new_rownames }
方法2:purrr包简洁实现(tidyverse风格)
如果习惯函数式编程,可以用purrr::map批量处理列表:
library(purrr) name_map <- setNames(master$rename, master$ID) # 批量修改列表中每个data.frame的行名 List <- map(List, function(x) { rownames(x) <- name_map[rownames(x)] x })
验证结果
运行代码后,打印列表即可确认结果符合预期:
print(List)
内容的提问来源于stack exchange,提问作者E Norton
相关产品推荐
相关产品推荐

