按组划分的最常见值(模式)[重复]

Posted

技术标签:

【中文标题】按组划分的最常见值(模式)[重复]【英文标题】:Most frequent value (mode) by group [duplicate] 【发布时间】:2015-05-29 02:42:00 【问题描述】:

我正在尝试按组查找最常见的值。在以下示例数据框中:

df<-data.frame(a=c(1,1,1,1,2,2,2,3,3),b=c(2,2,1,2,3,3,1,1,2))  
> df  
  a b  
1 1 2  
2 1 2  
3 1 1  
4 1 2  
5 2 3  
6 2 3  
7 2 1  
8 3 1  
9 3 2  

我想添加一个列“c”,当它的值按“a”分组时,它在“b”中出现次数最多。我想要以下输出:

> df  
  a b c  
1 1 2 2    
2 1 2 2    
3 1 1 2    
4 1 2 2    
5 2 3 3    
6 2 3 3    
7 2 1 3    
8 3 1 1   
9 3 2 1    

我尝试使用 table 和 tapply,但没有做对。有没有快速的方法来做到这一点? 谢谢!

【问题讨论】:

这个和this很相关 【参考方案1】:

以 Davids cmets 为基础,您的解决方案如下:

Mode <- function(x) 
  ux <- unique(x)
  ux[which.max(tabulate(match(x, ux)))]


library(dplyr)
df %>% group_by(a) %>% mutate(c=Mode(b))

请注意,当df$a3 时,b 的模式为1

【讨论】:

【参考方案2】:

我们可以使用 ave 获得按“a”分组的“b”的“模式”

 Mode <- function(x) 
 ux <- unique(x)
 ux[which.max(tabulate(match(x, ux)))]


df$c <-  with(df, ave(b, a, FUN=Mode))
df$c
#[1] 2 2 2 2 3 3 3 1 1

或使用data.table

library(data.table)
setDT(df)[, c:= Mode(b), by=a][]

【讨论】:

谢谢@akrun!要从模式函数中排除 NA,请将第二行更改为 'ux 【参考方案3】:

这是一个基本的 R 方法,它使用table 计算交叉表,max.col 查找每个组的模式,reprle 一起填写跨组的模式。

# calculate a cross tab, frequencies by group
myTab <- table(df$a, df$b)
# repeat the mode for each group, as calculated by colnames(myTab)[max.col(myTab)] 
# repeating by the number of times the group ID is observed
df$c <- rep(colnames(myTab)[max.col(myTab)], rle(df$a)$length)

df
  a b c
1 1 2 2
2 1 2 2
3 1 1 2
4 1 2 2
5 2 3 3
6 2 3 3
7 2 1 3
8 3 1 2
9 3 2 2

请注意,这假设数据已按组排序。此外,max.col 的默认设置是随机打破平局(多种模式)。如果您希望第一个或最后一个值成为模式,您可以使用 ties.method 参数进行设置。

【讨论】:

以上是关于按组划分的最常见值(模式)[重复]的主要内容,如果未能解决你的问题,请参考以下文章

在大熊猫DataFrame中按组删除异常值的更快方法[重复]

Pandas按组内的值分组和排序[重复]

在 Pandas 数据框中按组过滤具有最小值的行 [重复]

Mysql按组划分的百分比[关闭]

SQL:按组划分的最大可能日期范围

在 RecyclerView 中按组划分元素