2017-07-31 78 views
1

我有一系列我想要合并的数据帧,按顺序累加特定元素。对于背景,这些是用于基因组序列数据的单独分区文件,其参考沿着比对的基因区域(将其想象为字符串的部分)。我将序列对齐合并在一起,因此需要将分区文件合并在一起,同时保留分区相对位置。尽可能地将这一点尽可能地适应个别分区文件的任何数目和长度是很好的。R按顺序合并元素合并数据帧 - 棘手。

的合并和总结需要工作是这样的:

  1. 第二列元素是前行的第三列元素加一。
  2. 对于第一个数据帧,第三列:第一个元素等于n,第二个元素等于2n,第三个元素是3n,依此类推。
  3. 在新合并的数据帧中,第三列的第一个元素将成为其值(x)加上前一个数据帧(x +?n)中第三列的最后一个元素。然后将x添加到每行的x +?n,直到数据帧的结尾或新的一个合并为止。

一个简单的例子会更好地解释。

这里是1区的数据帧:

    V1 V2 V3 
Region_1_Partition_1  1 500 
Region_1_Partition_2 501 1000 
Region_1_Partition_3 1001 1500 

这里是区域2:

    V1 V2 V3 
Region_2_Partition_1  1 200 
Region_2_Partition_2 201 400 
Region_2_Partition_3 401 600 

最终分区文件需要是这样的:

    V1 V2 V3 
Region_1_Partition_1  1 500 
Region_1_Partition_2 501 1000 
Region_1_Partition_3 1001 1500 
Region_2_Partition_1 1501 1700 
Region_2_Partition_2 1701 1900 
Region_2_Partition_3 1901 2001 

我猜猜到目前为止,还有很多完美的解决方案无法解决!

感谢 Ç

回答

1

编辑:对不起,我平时浏览data.table()的具体问题,并没有注意到这个问题是关于数据帧!我相应地更改了我的答案

我会保留“n”作为列,以便您可以在最终框架中将其放入cumsum()。这我不会被merge而是由rbind()

首先实现“再造”数据

region1 <- data.frame(
    label=c('Region_1_Partition_1', 'Region_1_Partition_2', 
'Region_1_Partition_3'), 
    V4=500 
) 

region1$V3 <- cumsum(region1$V4) 
region1$V2 <- region1$V3 - region1$V4 + 1 
region1[, c('label', 'V2', 'V3')] 

最后一个命令返回

    label V2 V3 
1: Region_1_Partition_1 1 500 
2: Region_1_Partition_2 501 1000 
3: Region_1_Partition_3 1001 1500 

相似的代码,用V4=200可以给区域2。

现在执行你的组合,

out <- rbind(region1[, c('label', 'V4')], region2[, c('label', 'V4')]) 

out$V3 <- cumsum(out$V4) 
out$V2 <- out$V3 - out$V4 + 1 
out[, c('label', 'V2', 'V3')] 


        label V2 V3 
1: Region_1_Partition_1 1 500 
2: Region_1_Partition_2 501 1000 
3: Region_1_Partition_3 1001 1500 
4: Region_2_Partition_1 1501 1700 
5: Region_2_Partition_2 1701 1900 
6: Region_2_Partition_3 1901 2100 

ANOTHER编辑:如何扩展解决方案,以分区的更大的数字。

我可以在这里看到两个挑战,第一个是需要所有的东西,第二个是需要确定在V4列中使用什么。

有可能是这样(像存储在列表中的所有表,然后压扁下来,一个表)更有效的方式 - [R。我只会使用for循环。

比方说你有一个向量所有文件名叫做files

out <- data.frame() 
for (file in files) { 

    # read the file. prepend a path before this step if necessary 
    data <- read.csv(file) 

    # determine V4. This assumes that V3 is guaranteed to have a constant difference in any given file 
    # and that the first row is that difference, as in your example data 
    data$V4 <- data$V3[1] 

    data <- data[, c('V1', 'V4')] #note that I switched my first colname to match yours 

    out <- rbind(out, data) 
} 

# Recover V2 and V3 
out$V3 <- cumsum(out$V4) 
out$V2 <- out$V3 - out$V4 + 1 
out[, c('V1', 'V2', 'V3')] 

请注意,您的文件必须是为了,否则cumsum()不会是正确的。如果文件不是为了,你可以建立TE out表后,用cumsum()

+0

只是尝试这样做,效果很好,然后再重新订购。你有扩大的建议 - 说我非常为.csv 20+个别分区上的文件? –

+0

我已经编辑了答案,包括我试图解决这个问题 – HarlandMason