如何从数据中提取至少在连续两年出现的ID?
解决筛选连续年份出现的ID记录问题
嘿,这个问题我刚好有思路,咱们一步步来搞定它!你的需求是从数据框里提取那些至少在连续两年出现过的ID的所有记录对吧?比如ID5虽然出现两次,但年份是2006和2008不连续,所以要排除;而ID1、2、3、4、6都有连续年份的记录,需要保留。
首先先重现你的示例数据:
ID <- c(1, 2, 1, 3, 4, 2, 1, 5, 4, 1, 2, 6, 7, 3, 1, 2,6,9,5) Year <- c(2006, 2006, 2006, 2006, 2006, 2006, 2006,2006, 2007,2007,2007,2007,2007,2007,2007,2007,2008,2008,2008) DF <- data.frame(ID, Year)
下面给你两种常用的解决方案,你可以根据自己的习惯选择:
方法一:使用dplyr包(tidyverse风格)
这种方法代码可读性高,适合熟悉tidyverse的用户:
library(dplyr) # 第一步:找出所有符合条件的ID(存在连续年份的ID) valid_ids <- DF %>% group_by(ID) %>% # 对每个ID的年份去重后排序,检查是否有相邻年份差为1的情况 summarise(has_consecutive_years = any(diff(sort(unique(Year))) == 1), .groups = "drop") %>% filter(has_consecutive_years) %>% pull(ID) # 第二步:从原数据中筛选这些ID的所有记录 filtered_df <- DF %>% filter(ID %in% valid_ids) # 查看结果 print(filtered_df)
代码解释:
group_by(ID):按ID分组,每个组单独处理对应ID的年份数据sort(unique(Year)):先去除同一年份的重复值,再对年份排序,确保我们是按时间顺序检查连续性diff(...) == 1:计算相邻年份的差值,差值为1就代表这两年是连续的any(...):判断该ID是否存在至少一对连续年份pull(ID):把符合条件的ID提取成向量,方便后续过滤原数据
方法二:使用Base R(无需额外安装包)
如果你不想加载额外的包,用Base R也能实现:
# 第一步:获取每个ID对应的唯一年份列表(已排序) year_groups <- tapply(DF$Year, DF$ID, function(x) sort(unique(x))) # 第二步:筛选出存在连续年份的ID valid_ids <- names(which(sapply(year_groups, function(y) any(diff(y) == 1)))) # 把字符型的ID转换为数值型(因为tapply返回的名称是字符) valid_ids <- as.numeric(valid_ids) # 第三步:过滤原数据 filtered_df <- DF[DF$ID %in% valid_ids, ] # 查看结果 print(filtered_df)
结果验证
两种方法得到的结果都会保留ID为1、2、3、4、6的所有记录,ID5、7、9的记录会被排除,完全符合你的需求。
内容的提问来源于stack exchange,提问作者Davide Mirante
相关产品推荐
相关产品推荐

