如何在R中选择与其他组相关的一组数据中的最常见值?

3

我在R中有以下数据框:

ID = c(rep(1,5),rep(2,3),rep(3,2),rep(4,6));ID
VAR = c("A","A","A","A","B","C","C","D",
             "E","E","F","A","B","F","C","F");VAR
CATEGORY = c("ANE","ANE","ANA","ANB","ANE","BOO","BOA","BOO",
        "CAT","CAT","DOG","ANE","ANE","DOG","FUT","DOG");CATEGORY

DATA = data.frame(ID,VAR,CATEGORY);DATA

这看起来像是下面的表格:
ID VAR CATEGORY
1 A ANE
1 A ANE
1 A ANA
1 A ANB
1 B ANE
2 C BOO
2 C BOA
2 D BOO
3 E CAT
3 E CAT
4 F DOG
4 A ANE
4 B ANE
4 F DOG
4 C FUT
4 F DOG
期望的输出如下所示:
ID TEXTS category
1 A ANE
2 C BOO
3 E CAT
4 F DOG
更具体地说:我想要对于ID为1的行,找到VAR列中最常见的值A,然后基于最常见的A值查找CATEGORY列中最常见的值ANE,以此类推。
如何在R中实现此操作? 假设这是一个样本示例。我的实际数据框包含850,000行,有14,000个唯一的ID。
4个回答

6

使用countslice的另一种dplyr策略:

library(dplyr)
DATA %>% 
    group_by(ID) %>% 
    count(VAR, CATEGORY) %>% 
    slice(which.max(n)) %>% 
    select(-n)

     ID VAR   CATEGORY
  <dbl> <chr> <chr>   
1     1 A     ANE     
2     2 C     BOA     
3     3 E     CAT     
4     4 F     DOG  

3

dplyr

library(dplyr)
DATA %>%
  group_by(ID) %>%
  filter(VAR == names(sort(table(VAR), decreasing=TRUE))[1]) %>%
  group_by(ID, VAR) %>%
  summarize(CATEGORY = names(sort(table(CATEGORY), decreasing=TRUE))[1]) %>%
  ungroup()
# # A tibble: 4 x 3
#      ID VAR   CATEGORY
#   <dbl> <chr> <chr>   
# 1     1 A     ANE     
# 2     2 C     BOA     
# 3     3 E     CAT     
# 4     4 F     DOG     

数据

DATA <- structure(list(ID = c(1, 1, 1, 1, 1, 2, 2, 2, 3, 3, 4, 4, 4, 4, 4, 4), VAR = c("A", "A", "A", "A", "B", "C", "C", "D", "E", "E", "F", "A", "B", "F", "C", "F"), CATEGORY = c("ANE", "ANE", "ANA", "ANB", "ANE", "BOO", "BOA", "BOO", "CAT", "CAT", "DOG", "ANE", "ANE", "DOG", "FUT", "DOG")), class = "data.frame", row.names = c(NA, -16L))

2
我们可以修改 Mode 函数以返回索引,并在按“ID”分组后通过使用该索引在 slice 中进行操作。
Modeind <- function(x) {
   ux <- unique(x)
   which.max(tabulate(match(x, ux)))
   }
library(dplyr)
DATA %>%
     group_by(ID) %>%
     slice(Modeind(VAR)) %>%
     ungroup

-输出
# A tibble: 4 x 3
     ID VAR   CATEGORY
  <dbl> <chr> <chr>   
1     1 A     ANE     
2     2 C     BOO     
3     3 E     CAT     
4     4 F     DOG     

.@akrun,你的是唯一一个反映OP输出的。在ID 2中应该选择哪一个“BOA”还是“BOO”?两者都可以吗? - TarJae
1
@TarJae 在 Modeind 函数中,如果存在并列的情况,它只会选择第一个出现的。我不知道他们是否需要在这种情况下进行抽样。 - akrun
1
@TarJae,我注意到了。在那些没有明确顺序的情况下(除了展示的顺序),我倾向于推断关系不是很重要。如果发帖人需要其他东西,他们会说出来,或者在螺旋式开发中会显现出来。 - r2evans

2
一个使用嵌套的 subset + ave 的基础 R 选项
subset(
  subset(
    DATA,
    !!ave(ave(ID, ID, VAR, FUN = length), ID, FUN = function(x) x == max(x))
  ),
  !!ave(ave(ID, ID, VAR, CATEGORY, FUN = length), ID, VAR, FUN = function(x) seq_along(x) == which.max(x))
)

提供

   ID VAR CATEGORY
1   1   A      ANE
6   2   C      BOO
9   3   E      CAT
11  4   F      DOG

说明

  1. 内部的 subset + ave 是为了过滤掉具有最常见的 ID 分组后的 VAR 值的行。
  2. 根据前一步骤的修剪数据框,外部的 subset + ave 是为了过滤出具有最常见的 ID + VAR 分组后的 CATEGORY 值的行。

请您用自己的话解释一下这个逻辑,这样我可以更好地记忆。谢谢。 - TarJae
1
@TarJae 是的,现在已经添加了解释。 - ThomasIsCoding

网页内容由stack overflow 提供, 点击上面的
可以查看英文原文,
原文链接