Data.frame合并和选择2个Data.frames

时间:2016-02-18 14:46:38

标签: r merge dataframe

我有3个data.frames

> head(ON1)
  Entrez.ID Nearest.Refseq Gene.Name Tag.Count
1     11302      NM_007377      Aatk    137.48
2     11303      NM_013454     Abca1    118.09
3     11305      NM_007379     Abca2     93.56
4     11306      NM_009592     Abcb7     92.42
5     11308      NM_007380      Abi1    410.73
6     11356      NM_009598      Abl5    149.46

 > head(ON2)
  Entrez.ID Nearest.Refseq Gene.Name Tag.Count
1     11303      NM_013454     Abca1     86.02
2     11305      NM_007379     Abca2    103.45
3     11306      NM_009592     Abcb7     95.32
4     11308      NM_007380      Abi1    313.85
5     11350      NM_009594      Abl1    116.24
6     11352      NM_009595      Abl2    155.76

> head(ON3)
  Entrez.ID Nearest.Refseq Gene.Name Tag.Count
1     11303      NM_013454     Abca1     69.49
2     11305      NM_007379     Abca2     82.02
3     11306      NM_009592     Abcb7     83.16
4     11308      NM_007380      Abi1    306.44
5     11350      NM_009594      Abl1    150.37
6     11355      NM_009599      Abl4    154.93

有些行只有1个data.frame(例如row1 ON1),有些行在2个data.frames中很常见(例如row5 ON2ON3,此行在ON1}中不存在,有些在所有data.frames中都很常见(例如row2 ON1 row1ON2ON3)中。 唯一的区别是上一栏Tag.Count

中的值

我想以这样的方式合并所有3个data.frames,我只获得最终data.frame中的那些行,这些行在至少2个data.frames和Tag.Count的值中是常见的。其中较高者将被分配到该行。

> head(F)
  Entrez.ID Nearest.Refseq Gene.Name Tag.Count
1     11303      NM_013454     Abca1     118.09
2     11305      NM_007379     Abca2     103.45
3     11306      NM_009592     Abcb7     95.32
4     11308      NM_007380      Abi1    410.73
5     11350      NM_009594      Abl1    150.37

在这里,您会看到Entrez.ID = 11302的行被删除,因为它只在所有data.frames中出现一次,而且至少有2个data.frames中常见的行出现在这里但是所有data.frames中最大的Tag.Count分数被分配到该行。

更新

如何获取行的平均值。在合并上述三个数据集之后,我想要将Tag.count值相加并除以具有相同Tag.count的总行数,而不是仅保留一行具有最大Entrez.ID值的行。实际上,前3列中的值是相同的,差异仅出现在最后一列中。 例如:

> head(d)
      Entrez.ID Nearest.Refseq Gene.Name Tag.Count
1         11302      NM_007377      Aatk    137.48
2         11303      NM_013454     Abca1    118.09
7886      11303      NM_013454     Abca1     86.02
15407     11303      NM_013454     Abca1     69.49
3         11305      NM_007379     Abca2     93.56
7887      11305      NM_007379     Abca2    103.45

因此,在这种情况下,3行有Entrez.ID = 11303,Tag.count值将被总结(118.09 + 86.02 + 69.49)并除以3,最终输出将只包含1行Entrez.ID 11303和Tag.Count value =总和/行数

3 个答案:

答案 0 :(得分:3)

这是一种组合三个数据帧的方法。合并所有三个后,我们发现不止一次出现的值。使用该索引,我们可以使用函数max聚合数据框:

d <- do.call(rbind, list(ON1, ON2, ON3))
d1 <- do.call(paste, d[1:3])
tbl <- table(d1) > 1L
indx <- d1 %in% names(tbl[tbl])
aggregate(Tag.Count ~., d[indx,], FUN=max)
#   Entrez.ID Nearest.Refseq Gene.Name Tag.Count
# 1     11303      NM_013454     Abca1    118.09
# 2     11305      NM_007379     Abca2    103.45
# 3     11306      NM_009592     Abcb7     95.32
# 4     11308      NM_007380      Abi1    410.73
# 5     11350      NM_009594      Abl1    150.37

答案 1 :(得分:1)

您可以通过将三者绑定在一起,使用一个元素过滤掉组,然后在每个组中选择顶部Tag.Count,在dplyr中执行此操作。

library(dplyr)

F <- bind_rows(ON1, ON2, ON3) %>%
  group_by(Entrez.ID) %>%    # elements are in same group if same Entrez.ID
  filter(n() > 1) %>%        # filter out groups with 1 element
  top_n(1, Tag.Count)        # pick highest Tag.Count from each

答案 2 :(得分:0)

关于更新:

预赛

tab <- structure(
  list(
    Entrez.ID = c(11302L, 11303L, 11303L, 11303L, 11305L, 11305L),
    Nearest.Refseq = structure(c(1L, 3L, 3L, 3L, 2L, 2L),
                               .Label = c("NM_007377", "NM_007379", "NM_013454"),
                               class = "factor"),
    Gene.Name = structure(c(1L, 2L, 2L, 2L, 3L, 3L),
                          .Label = c("Aatk", "Abca1", "Abca2"),
                          class = "factor"),
    Tag.Count = c(137.48, 118.09, 86.02, 69.49, 93.56, 103.45)
  ),
  .Names = c("Entrez.ID", "Nearest.Refseq", "Gene.Name", "Tag.Count"),
  class = "data.frame",
  row.names = c("1", "2", "7886", "15407", "3", "7887")
)
print(tab)
#       Entrez.ID Nearest.Refseq Gene.Name Tag.Count
# 1         11302      NM_007377      Aatk    137.48
# 2         11303      NM_013454     Abca1    118.09
# 7886      11303      NM_013454     Abca1     86.02
# 15407     11303      NM_013454     Abca1     69.49
# 3         11305      NM_007379     Abca2     93.56
# 7887      11305      NM_007379     Abca2    103.45

dplyr方式

library(dplyr)
(res <- tab %>% group_by(Entrez.ID) %>% filter(n() > 1) %>% summarise(Means = mean(Tag.Count)))

结果:

  Entrez.ID   Means
      (int)   (dbl)
1     11302 137.480
2     11303  91.200
3     11305  98.505
在大卫·阿伦堡发表评论之后

纯粹的data.table方式

library(data.table)
(res <- setDT(tab)[, if(.N > 1) { .(Means = mean(Tag.Count)) }, by = Entrez.ID])

结果与上述相同。

保留Nearest.RefseqGene.Name

两种可能的dplyr解决方案,选择一个:

假设Nearest.RefseqGene.Name对于每个Gene.Name都是唯一的:

res <- tab %>% group_by(Entrez.ID) %>% summarise(Nearest.Refseq = Nearest.Refseq[1], Gene.Name = Gene.Name[1], Means = mean(Tag.Count))

如果不是,你需要对它们做些什么(替换someFunction()!):

res <- tab %>% group_by(Entrez.ID) %>% summarise(Nearest.Refseq = someFunction(Nearest.Refseq), Gene.Name = someFunction(Gene.Name), Means = mean(Tag.Count))

修改:已删除混合data.table / dplyr方法。