【发布时间】:2020-02-29 13:32:50
【问题描述】:
我有一个数据框target,其中包含SNP 和value 列:
target <- data.frame("SNP" = c("rs2", "rs4", "rs6", "rs19", "rs8", "rs9"),
"value" = 1:6)
我还有 3 个其他数据框,其中包含 SNP 和 int 列作为列表:
ref1 <- data.frame("SNP" = c("rs1", "rs2", "rs8"), "int" = c(5, 7, 88))
ref2 <- data.frame("SNP" = c("rs9", "rs4", "rs3"), "int" = c(23, 4, 43))
ref3 <- data.frame("SNP" = c("rs10", "rs6", "rs5"), "int" = c(53, 22, 76))
mylist <- list(ref1, ref2, ref3)
我想为target 添加一个新列int,其值对应于具有相同SNP 的ref1/2/3 的int 值。例如,target 的第一个 int 值应该是 7,因为 ref1 的第 2 行具有 rs2 的 SNP 和 7 的 int。
我尝试了以下代码:
for (i in 1:3) {
target <- target %>%
left_join(mylist[[i]], by = "SNP")
}
匹配快速且成功。但是,我返回了 3 个新列而不是 1 个,如下所示:
然后我使用了以下代码:
target[, "ref"] <- NA
for (i in 1:3) {
common <- Reduce(intersect, list(target$SNP, mylist[[i]]$SNP))
tar.pos <- match(common, target$SNP)
ref.pos <- match(common, mylist[[i]]$SNP)
target$ref[tar.pos] <- mylist[[i]]$int[ref.pos]
}
在我的真实数据中,我有 22 个参考数据帧,每个数据帧有 1-6 百万行。我宁愿通过 ref 进行匹配和加入 ref,而不是将所有 ref 合并到一个大数据中。当我在我的真实数据上尝试上面的第二种方法时,我注意到match 函数工作得非常慢。这就是为什么我更喜欢一些聪明的工作方式。我发现 left_join 即使对于我的大数据也工作得非常快。不幸的是,输出并不是我想要的。
我希望快速完成上述工作,最好是在 tidyverse 中。关于如何修改第一种编码方法或任何其他更聪明的方法,有什么建议吗?
【问题讨论】: