R语言如何新增列标识各id分组下缺失的score类别
R语言按分组识别缺失score类别实现方案
核心实现逻辑:按id分组后,基于每组的max.score生成0到该值的完整整数序列,与组内实际出现的去重score值做差集得到缺失类别,按要求拼接后回填到分组所有行,无缺失则填充NA。
方法1:dplyr实现(代码简洁易读)
适合习惯用tidyverse语法的场景,代码如下:
library(dplyr) # 初始化示例数据 df <- data.frame(id = c(1,1,1,1,1, 2,2,2,2,2, 3,3,3,3,3), score = c(0,0,2,0,2, 0,1,1,0,1, 0,1,0,1,0), max.score = c(2,2,2,2,2, 1,1,1,1,1, 2,2,2,2,2)) df <- df %>% group_by(id) %>% mutate( # 生成该组应该覆盖的完整score序列 full_score = list(0:unique(max.score)), # 提取组内实际存在的score值 exist_score = list(unique(score)), # 取差集得到缺失值 miss_val = setdiff(unlist(full_score), unlist(exist_score)), # 按规则生成missing列 missing = ifelse(length(miss_val) == 0, NA_character_, paste(miss_val, collapse = ",")) ) %>% # 删除计算用的临时列 select(-full_score, -exist_score, -miss_val) %>% ungroup()
执行代码后得到的结果与期望输出完全匹配,多缺失值场景会自动用逗号拼接。
方法2:基础R实现(无需安装第三方包)
不依赖额外扩展包即可实现,代码如下:
# 初始化示例数据 df <- data.frame(id = c(1,1,1,1,1, 2,2,2,2,2, 3,3,3,3,3), score = c(0,0,2,0,2, 0,1,1,0,1, 0,1,0,1,0), max.score = c(2,2,2,2,2, 1,1,1,1,1, 2,2,2,2,2)) # 按id拆分数据 df_split <- split(df, df$id) # 逐组计算缺失值 df_split <- lapply(df_split, function(subdf) { full_val <- 0:unique(subdf$max.score) exist_val <- unique(subdf$score) miss_val <- setdiff(full_val, exist_val) subdf$missing <- if (length(miss_val) == 0) NA else paste(miss_val, collapse = ",") subdf }) # 合并为完整数据框 df <- do.call(rbind, df_split) rownames(df) <- NULL
注意事项
- 逻辑默认同一
id分组下max.score取值一致,若同id存在多个不同max.score,可根据业务规则调整取值(例如取分组内最大值) - 输出的
missing列为字符类型,若后续需要对缺失值做数值运算,可再做拆分转换 - 自动适配多缺失值场景:例如某组
max.score=3、实际仅出现score=0,会自动返回拼接结果1,2,3
内容的提问来源于stack exchange,提问作者amisos55
相关产品推荐
相关产品推荐

