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

R语言如何筛选每个student_id对应English和Spanish测试各1条观测值

问题描述

我有如下数据框:

student_id <- c(1,1,1,2,2,2)
test_score <- c(100, 90, 80, 100, 70, 90)
test_type <- c("English", "English", "English", "Spanish", "Spanish", "Spanish")
time_period <- c(1, 0, 1, 0, 1, 0)
df <- data.frame(student_id, test_score, test_type, time_period)

我需要筛选观测值,实现每个student_id都有English和Spanish测试各一条记录,我尝试了如下代码:

df <- df %>%
group_by(student_id, test_type) %>%
dplyr::filter(row_number() == 1)

但运行后仅返回English测试的相关结果,请问如何实现每个student_id的English和Spanish测试各返回一条观测值?


解答

问题原因

你给出的示例数据集本身存在测试类型缺失:student_id=1的所有观测都只有English测试记录,没有Spanish测试记录;student_id=2的所有观测都只有Spanish测试记录,没有English测试记录。你原有代码按student_id和test_type分组后取每组第一条,自然只会返回每个学生已有的测试类型的第一条记录,无法同时返回两种测试类型的结果。

解决方法

分两种常见场景选择对应方案:

场景1:你的完整数据集里每个学生实际有两种测试类型的记录,示例数据是简化版本

你原有代码的逻辑本身是成立的,只需要根据你的业务需求调整组内排序规则,确保取到的第一条是你需要的记录即可,比如要取time_period最新的记录可以这么写:

library(dplyr)
df <- df %>%
  group_by(student_id, test_type) %>%
  # 按组内time_period降序排序,取最新的一条记录
  arrange(desc(time_period), .by_group = TRUE) %>%
  filter(row_number() == 1) %>%
  ungroup()

场景2:需要强制给每个学生补全两种测试类型的记录,缺失的记录留空/填默认值

可以搭配tidyr::complete补全学生和测试类型的全组合,再按分组取数:

library(dplyr)
library(tidyr)
df_result <- df %>%
  # 补全所有student_id和test_type的组合
  complete(student_id, test_type) %>%
  group_by(student_id, test_type) %>%
  filter(row_number() == 1) %>%
  ungroup()

内容的提问来源于stack exchange,提问作者epi-rmeister

相关产品推荐
方舟 Agent Plan

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

最近更新时间:2026.10.10 22:21:02