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

R语言按行筛选数值大于0单元格并保留原始文本的实现方法

问题描述
  • 现有如下数据集:
dat <- structure(list(rn = c("A", "B", "C", 
"D", "E"), `[0,25)` = c("40 (replaced)", 
"52 (replaced)", "5", "2", "5 (replaced)"), `[25,50)` = c("0 (replaced)", 
"0 (replaced)", "0 (replaced)", "0 (replaced)", "0 (replaced)"), `[25,100)` = c("5", 
"3", "38", "2", "1"), `[50,100)` = c("0 (replaced)", "0 (replaced)", 
"0 (replaced)", "0 (replaced)", "0 (replaced)")), row.names = c(NA, 
-5L), class = c("data.table", "data.frame"))

# 数据预览
dat
#    rn        [0,25)      [25,50) [25,100)     [50,100)
# 1:  A 40 (replaced) 0 (replaced)        5 0 (replaced)
# 2:  B 52 (replaced) 0 (replaced)        3 0 (replaced)
# 3:  C             5 0 (replaced)       38 0 (replaced)
# 4:  D             2 0 (replaced)        2 0 (replaced)
# 5:  E  5 (replaced) 0 (replaced)        1 0 (replaced)
  • 此前可通过如下代码提取单元格内的数值,筛选出每行数值大于0的结果:
dat <- t(apply(dat, 1, extract_numeric))
dat <- as.data.frame(dat )
dat <- dat %>% 
    rowwise() %>% 
    summarise(V1 = V1, freq =list(c_across(-V1))) %>% 
    rowwise() %>% 
    mutate(freq = list(freq[which(freq > 0)]))

对应输出结果示例:
结果示例

dat_out <- structure(list(V1 = c(NA_real_, NA_real_, NA_real_, NA_real_, 
NA_real_), freq = list(c(40, 5), c(52, 3), c(5, 38), c(2, 2), 
    c(5, 1))), class = c("rowwise_df", "tbl_df", "tbl", "data.frame"
), row.names = c(NA, -5L), groups = structure(list(.rows = structure(list(
    1L, 2L, 3L, 4L, 5L), ptype = integer(0), class = c("vctrs_list_of", 
"vctrs_vctr", "list"))), row.names = c(NA, -5L), class = c("tbl_df", 
"tbl", "data.frame")))
  • 需求:在筛选逻辑不变的基础上,保留对应单元格的原始文本内容,而非仅保留提取后的数值。
    期望输出格式如下:
freq
c("40 (replaced)","5")
c("52 (replaced)","3")
c("5","38")
c("2","2")
c("5 (replaced)","1")
实现方案

核心逻辑是按行遍历非分组列时,同步保留原始文本和提取出的数值,仅保留数值大于0对应的原始文本即可,无需先把整个数据集转成数值矩阵丢失原始信息。
完整可运行代码:

library(tidyverse)
# 如未安装readr可先运行 install.packages("readr"),parse_number用于提取字符串里的数值

# 读取/构造原始数据
dat <- structure(list(rn = c("A", "B", "C", 
"D", "E"), `[0,25)` = c("40 (replaced)", 
"52 (replaced)", "5", "2", "5 (replaced)"), `[25,50)` = c("0 (replaced)", 
"0 (replaced)", "0 (replaced)", "0 (replaced)", "0 (replaced)"), `[25,100)` = c("5", 
"3", "38", "2", "1"), `[50,100)` = c("0 (replaced)", "0 (replaced)", 
"0 (replaced)", "0 (replaced)", "0 (replaced)")), row.names = c(NA, 
-5L), class = c("data.table", "data.frame"))

# 处理得到结果
result <- dat %>%
  rowwise() %>%
  summarise(
    rn = rn,
    # 提取除rn列外的所有单元格值,筛选数值>0对应的原始文本
    freq = list(
      cell_vals = c_across(-rn) %>% unlist(use.names = FALSE),
      cell_nums = readr::parse_number(cell_vals),
      cell_vals[cell_nums > 0]
    )[[3]]
  ) %>%
  ungroup()

运行后查看结果:

# 查看freq列内容
result$freq
# 输出完全匹配预期
[[1]]
[1] "40 (replaced)" "5"            

[[2]]
[1] "52 (replaced)" "3"            

[[3]]
[1] "5"  "38"

[[4]]
[1] "2" "2"

[[5]]
[1] "5 (replaced)" "1"            

如果需要和之前的输出结构完全一致,去掉rn = rn这一行即可,最终输出仅保留freq列。

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

相关产品推荐
方舟 Agent Plan

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

最近更新时间:2026.08.29 20:57:15