如何用data.table移除指定列全为NA的数据行?
使用data.table移除指定列全为NA的数据行
需求
需要移除指定相关列全为NA的数据行,无关列是否为NA不影响。示例中仅需移除第2行(rel_1和rel_2全为NA),保留第1行(rel_2有值)和第3行(两列均有值)。
示例数据与错误尝试
library(data.table) df <- data.frame( epoch = c(1,2,3), irrel_2 = c(NA,4,5), rel_1 = c(NA, NA, 8), rel_2 = c(3,NA,7) ) df #> epoch irrel_2 rel_1 rel_2 #> 1 1 NA NA 3 #> 2 2 4 NA NA #> 3 3 5 8 7 setDT(df) # 错误:na.omit会移除指定列中存在NA的所有行,不符合需求 wrong <- na.omit(df, cols = 3:4)
解决方案
方法1:通过行内NA计数筛选
先定义相关列,再用rowSums统计每行相关列的NA数量,仅保留NA数量不等于列总数的行:
rel_cols <- c("rel_1", "rel_2") result <- df[rowSums(is.na(.SD)) != length(rel_cols), .SDcols = rel_cols]
方法2:逐列逻辑判断合并
用Reduce把每列的NA判断结果按行合并为“是否全为NA”的逻辑值,取反后筛选:
rel_cols <- c("rel_1", "rel_2") result <- df[!Reduce(`&`, lapply(.SD, is.na)), .SDcols = rel_cols]
方法3:直接写逻辑条件(列数少的情况)
如果相关列数量不多,直接写出逻辑判断更直观:
result <- df[!(is.na(rel_1) & is.na(rel_2))]
验证结果
运行任意一种方法后,result的输出为:
epoch irrel_2 rel_1 rel_2 1: 1 NA NA 3 2: 3 5 8 7
完全符合需求。
内容的提问来源于stack exchange,提问作者Andi
相关产品推荐
相关产品推荐

