新答案
我会编写如下函数来拆分列:
splitFun <- function(inVec, sep = ",", newName = "ALT", fill = NA) {
if (!is.character(inVec)) inVec <- as.character(inVec)
X <- strsplit(inVec, sep, fixed = TRUE)
cols <- vapply(X, length, 1L)
M <- matrix(
fill, nrow = length(inVec), ncol = max(cols),
dimnames = list(NULL, make.unique(rep(newName, max(cols)), sep="")))
M[cbind(rep(sequence(length(X)), cols), sequence(cols))] <-
unlist(X, use.names=FALSE)
M
}
用法很简单:
splitFun(mydf$ALT) ## Modify default arguments accordingly
# ALT ALT1 ALT2
# [1,] "AA" "AT" NA
# [2,] "GCGCG" "AGCG" NA
# [3,] "GCGCG" "AT" "AA"
cbind(mydf, splitFun(mydf$ALT))
# CHOM POS REF ALT ALT ALT1 ALT2
# 1 1 121 A AA,AT AA AT <NA>
# 2 2 254 GCGC GCGCG,AGCG GCGCG AGCG <NA>
# 3 1 123 GCGC GCGCG,AT,AA GCGCG AT AA
时间应该是相当有效的。这是与“splitstackshape”方法(也可以处理不平衡情况)的比较。
system.time(splitstackshape:::read.concat(
bigDf$ALT, sep=",", col.prefix="ALT"))
# user system elapsed
# 1.197 0.000 1.202
system.time(splitFun(bigDf$ALT))
# user system elapsed
# 0.069 0.000 0.068
对于上述情况,使用的样本数据为:
mydf <- data.frame(CHOM = c(1, 2, 1), POS = c(121, 254, 123),
REF = c("A", "GCGC", "GCGC"),
ALT = c("AA,AT", "GCGCG,AGCG", "GCGCG,AT,AA"))
mydf
# CHOM POS REF ALT
# 1 1 121 A AA,AT
# 2 2 254 GCGC GCGCG,AGCG
# 3 1 123 GCGC GCGCG,AT,AA
bigDf <- do.call(rbind, replicate(10000, mydf, simplify = FALSE))
旧答案
你可以试试我的“splitstackshape”包中的concat.split:
library(splitstackshape)
concat.split(mydf, "ALT", ",") ## Add `drop = TRUE` to drop the original column
# CHOM POS REF ALT ALT_1 ALT_2
# 1 1 121 A AA,AT AA AT
# 2 2 254 GCGC GCGCG,AGCG GCGCG AGCG
还有来自“reshape2”包的colsplit:
library(reshape2)
colsplit(as.character(mydf$ALT), ",", c("ALT", "ALT1"))
# ALT ALT1
# 1 AA AT
# 2 GCGCG AGCG
您可以使用cbind 将输出添加到您的原始数据集中。