合并数据框中的列以获取r中的可变列数

时间:2015-03-31 17:16:36

标签: r

我有一个数据框如下。我想从V2开始合并列(pref与公共之间),但在合并列中排除NA。每行中都有可变数量的列和NA。

V1                          V2    V3        V4     V5       V6         V7    
chr11:69464719-69502928    CCND1 ORAOV1     NA     NA       NA         NA     
chr7:55075808-55093954     EGFR    NA       NA     NA       NA         NA     
chr3:169389459-169490555   TERC   ARPM1     NA     NA       NA         NA     
chr1:150496857-150678056   ENSA   MCL1   ADAMTSL4 GOLPH3L   HORMAD1  MIR4257

我想要的结果是:

V1                          V2
chr11:69464719-69502928    CCND1,ORAOV1
chr7:55075808-55093954     EGFR
chr3:169389459-169490555   TERC,ARPM1
chr1:150496857-150678056   ENSA,MCL1,ADAMTSL4,GOLPH3L,HORMAD1,MIR4257

我知道如何连接固定列但是排除NA的变量列引发了我的兴趣。

1 个答案:

答案 0 :(得分:3)

我们可以使用apply使用MARGIN=1(不包括第1列)来循环行,paste非NA元素(toString是{paste(., collapse=', ')的包装1}})

V2 <- apply(df1[-1],1, function(x) toString(x[!is.na(x)]))
res <- data.frame(V1=df1[,1], V2, stringsAsFactors=FALSE)
res
#                       V1                                              V2
#1  chr11:69464719-69502928                                   CCND1, ORAOV1
#2   chr7:55075808-55093954                                            EGFR
#3 chr3:169389459-169490555                                     TERC, ARPM1
#4 chr1:150496857-150678056 ENSA, MCL1, ADAMTSL4, GOLPH3L, HORMAD1, MIR4257

或者使用melt中的data.table,将数据集转换为long表单,按'V1'分组,将paste转换为'value'列的元素。最初,我们使用setDT将'data.frame'转换为'data.table'。

library(data.table)
melt(setDT(df1), id.var='V1', na.rm=TRUE)[, list(V2=toString(value)) , V1]
#                        V1                                              V2
#1:  chr11:69464719-69502928                                   CCND1, ORAOV1
#2:   chr7:55075808-55093954                                            EGFR
#3: chr3:169389459-169490555                                     TERC, ARPM1
#4: chr1:150496857-150678056 ENSA, MCL1, ADAMTSL4, GOLPH3L, HORMAD1, MIR4257

数据

df1 <- structure(list(V1 = c("chr11:69464719-69502928", 
"chr7:55075808-55093954", 
"chr3:169389459-169490555", "chr1:150496857-150678056"),
V2 = c("CCND1", 
"EGFR", "TERC", "ENSA"), V3 = c("ORAOV1", NA, "ARPM1", "MCL1"
), V4 = c(NA, NA, NA, "ADAMTSL4"), V5 = c(NA, NA, NA, "GOLPH3L"
), V6 = c(NA, NA, NA, "HORMAD1"), V7 = c(NA, NA, NA, "MIR4257"
)), .Names = c("V1", "V2", "V3", "V4", "V5", "V6", "V7"), 
class = "data.frame", row.names = c(NA, -4L))