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

使用dplyr的group_by移除含多NA行并合并p_id唯一行

解决按p_id合并行并移除多余NA的问题

嘿,这需求很常见,我来给你两个靠谱的解决方案,不管你用dplyr还是base R都能搞定,而且支持任意列数哦!

先看你的原始数据

首先把你的测试数据放出来,方便对照:

df <- data.frame(id=c(1,1,2,3,4,4),p_id=c(1001,1001,1002,1003,1004,1004),x=c(1,NA,1,2,NA,1),y=c(NA,5,4,NA,6,NA),z=c(NA,NA,2,3,NA,4))

对应的表格:

idp_idxyz
110011NANA
11001NA5NA
21002142
310032NA3
41004NA6NA
410041NA4

方案一:用dplyr(推荐,代码更直观)

如果你习惯用tidyverse系列工具,这个方案最顺手,扩展性拉满,加多少列都不用改代码:

library(dplyr)

# 核心处理代码
result <- df %>%
  group_by(p_id) %>%
  # 对除id外的所有列处理,自动适配任意列数
  summarise(across(-id, ~{
    non_na_vals <- na.omit(.x)
    if (length(non_na_vals) > 0) non_na_vals[1] else NaN
  }), .groups = "drop")

# 查看结果
print(result)

代码解释

  • group_by(p_id):把相同p_id的行归为一组,这是合并的基础
  • across(-id, ...):指定要处理的列,-id表示排除id列,剩下的所有列(不管是x、y、z还是以后新增的列)都会被处理,完美支持任意列数
  • 自定义函数逻辑:对每组的列数据,先过滤掉NA值,如果有非NA值就取第一个(你的数据里每组同一列只有一个非NA值),如果全是NA就返回NaN,和你期望的输出完全匹配
  • .groups = "drop":处理完后取消分组结构,得到普通的数据框

方案二:用base R(无需额外安装包)

如果不想加载dplyr,用base R的aggregate函数也能实现:

# base R 版本代码
result_base <- aggregate(. ~ p_id, data = df[, -1], FUN = function(x) {
  non_na_vals <- na.omit(x)
  if (length(non_na_vals) > 0) non_na_vals[1] else NaN
})

# 查看结果
print(result_base)

代码解释

  • aggregate(. ~ p_id, data = df[, -1], ...):按p_id分组,对df[, -1](去掉id列后的所有数据)应用自定义函数
  • 自定义函数的逻辑和dplyr版本完全一致,最终效果也相同

最终输出结果

不管用哪个方案,你都会得到想要的结果:

p_idxyz
100115NaN
1002142
10032NaN3
1004164

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

相关产品推荐
方舟 Agent Plan

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

最近更新时间:2026.05.26 10:28:21