You need to enable JavaScript to run this app.
优惠活动
大模型
产品
解决方案
定价
更多

使用dplyr高效筛选符合指定二选一条件的分组(适配大数据集)

高效筛选符合条件的分组(适配大数据集)

需求说明

我们需要从数据集中筛选出满足以下任一条件的分组(按id分组):

  • 分组同时包含值a和b
  • 分组同时包含值a和c

给定测试数据集:

ff <- data.frame(id = c(1,1,2,2,3,3,4,4), value = c("a", "a", "a", "b", "a", "c", "b", "c"))

预期筛选结果为id=2和id=3的分组。


方法1:使用data.table(推荐大数据集)

data.table针对大数据集的分组操作做了深度优化,内存占用低、运行速度快,适合百万级以上数据量。

library(data.table)
setDT(ff)

# 第一步:筛选符合条件的id
valid_ids <- ff[, .(unique_vals = unique(value)), by = id][
  (("a" %in% unique_vals) & ("b" %in% unique_vals)) | (("a" %in% unique_vals) & ("c" %in% unique_vals)), 
  id
]

# 第二步:提取原数据中符合条件的行(按需执行)
filtered_data <- ff[id %in% valid_ids]

核心逻辑:先按id分组去重value,减少重复判断的计算量;再通过向量化条件筛选出目标id,最后过滤原数据。


方法2:使用dplyr(tidyverse生态,代码简洁)

dplyr的向量化分组操作同样高效,配合tidyverse工具链可无缝对接数据导入、清洗流程。

library(dplyr)

# 筛选符合条件的id
valid_ids <- ff %>%
  group_by(id) %>%
  summarize(
    has_a = any(value == "a"),
    has_b = any(value == "b"),
    has_c = any(value == "c"),
    .groups = "drop"
  ) %>%
  filter((has_a & has_b) | (has_a & has_c)) %>%
  pull(id)

# 提取目标数据
filtered_data <- ff %>% filter(id %in% valid_ids)

核心逻辑:分组后用any()快速判断每个分组是否包含目标值,再通过逻辑条件筛选id,避免逐行循环。


方法3:Base R实现(无需第三方包)

如果不想加载额外包,可使用Base R的tapply和向量化判断实现高效筛选:

# 按id分组获取唯一value集合
id_value_sets <- tapply(ff$value, ff$id, unique)

# 判断每个分组是否符合条件
valid_ids <- names(id_value_sets)[sapply(id_value_sets, function(vals) {
  (("a" %in% vals) & ("b" %in% vals)) | (("a" %in% vals) & ("c" %in% vals))
})]

# 筛选原数据
filtered_data <- ff[ff$id %in% valid_ids, ]

高效优化关键点

  • 分组前去重:避免对同一分组内的重复值做多次判断,减少计算量
  • 向量化操作:所有方法均使用向量化判断替代逐行循环,速度提升显著
  • 内存控制:优先筛选id再过滤原数据,避免对全量数据做不必要的操作

内容的提问来源于stack exchange,提问作者cliu

相关产品推荐
方舟 Agent Plan

超全模态模型 × Harness 升级,最新支持 Deepseek-V4.1-Flash、GLM-5.3 系列、Doubao-Seedream-5.0-pro、Kimi-K3 (部分), 限时 9.9 元起

最近更新时间:2026.07.18 20:40:34