R语言如何筛选多列含指定字符串的行并完成受试者分组
R语言实现纵向数据集筛选与分组的最优方案
方案说明
采用tidyverse生态的dplyr+stringr实现,代码简洁易读,适配纵向数据的行级筛选和受试者级分组需求,也提供Base R无依赖备选方案。
前置准备
- 安装加载依赖包
# 未安装的话先执行 install.packages("tidyverse") library(tidyverse)
- 构造示例数据集
df <- tibble( id = c(1,1,2,2,2,3,4,4,5), dg1 = c("A1","B3","B5","C1","D1","D1","E1","E2","F1"), dg2 = c("F1","A13","D1","C1","C1","B4","B1","B7","B3"), dg3 = c("D1","C1","B1","B4","B5","D1","G1","F1","D1"), dg4 = c("B3","B5","B6","B2","A1","C2","C3","S13","B2"), agegroup = c(1,2,1,2,3,1,2,3,1) )
需求1:多列匹配筛选行
首先定义要匹配的目标字符串向量,用if_any()对所有dg开头的列做批量判断,只要任意一列命中就保留该行:
# 定义待匹配的目标字符串 target_str <- c("A1", "A13", "B1", "B2") # 筛选符合条件的行,保留所有原始列 df_filtered <- df %>% filter(if_any(starts_with("dg"), ~ .x %in% target_str))
如果需要模糊匹配(只要包含目标字符串就算命中,不需要完全相等),把判断条件替换为str_detect(.x, paste(target_str, collapse = "|"))即可。
需求2:按受试者(id)划分组别
因为是受试者级别的分组,只要该id下存在任意一行符合筛选条件,就划分为A组,否则划分为B组:
df_with_group <- df %>% group_by(id) %>% mutate( has_target = any(if_any(starts_with("dg"), ~ .x %in% target_str)), group = ifelse(has_target, "A", "B") ) %>% ungroup() %>% select(-has_target) # 可选,删除中间判断列
执行后group列就是对应的分组结果,示例数据中仅id=3没有命中记录,会被划分为B组,其余id均为A组。
备选:Base R无依赖实现方案
如果不想加载第三方包,可以用原生语法实现:
target_str <- c("A1", "A13", "B1", "B2") # 定位dg列的索引 dg_cols <- grep("^dg", colnames(df)) # 需求1:筛选行 df_filtered <- df[rowSums(sapply(df[dg_cols], function(x) x %in% target_str)) > 0, ] # 需求2:分组 df$group <- ave( rowSums(sapply(df[dg_cols], function(x) x %in% target_str)) > 0, df$id, FUN = function(x) ifelse(any(x), "A", "B") )
内容的提问来源于stack exchange,提问作者birch
相关产品推荐
相关产品推荐

