求助:R语言detectaOutliers()函数无法删除全部异常值,恳请排查问题
排查你的
detectaOutliers()函数问题 先看你的函数核心问题:它并没有实现「删除异常值」的逻辑,只是生成了一个标记中度异常值的列,这是最关键的问题。除此之外还有几个小细节会导致异常值识别不完整,我一步步给你拆解:
问题分析
- 核心逻辑缺失:你的函数最后返回的是标记异常值的矩阵,但完全没有编写「删除这些异常值」的代码。你可能误以为标记后自动会删除,但实际上需要额外步骤过滤数据。
- 未处理NA值:
quantile(x, probs = c(0.25, 0.75))默认不会忽略NA,如果你的输入向量x里有缺失值,会导致分位数计算结果为NA,后续所有异常值阈值(OM1、OM3等)都会变成NA,标记逻辑直接失效。 - 极端异常值未利用:你定义了
extremos变量标记极端异常值,但最后返回的是moderados的结果,极端异常值的判断完全没用到,会漏掉这部分异常值。
修复后的函数
我帮你调整了函数,让它既能正确识别所有异常值(中度+极端),也可以直接返回删除异常值后的向量,同时处理了NA值:
detectaYEliminaOutliers = function(x, eliminar = TRUE) { # 处理NA值,计算分位数时忽略NA q = quantile(x, probs = c(0.25, 0.75), na.rm = TRUE) R = IQR(x, na.rm = TRUE) # 计算中度和极端异常值阈值 OM1 = q[1] - (R * 1.5) OM3 = q[2] + (R * 1.5) OE1 = q[1] - (R * 3) OE3 = q[2] + (R * 3) # 标记所有异常值:中度或极端都算异常 es_outlier = ifelse(x < OM1 | x > OM3 | x < OE1 | x > OE3, TRUE, FALSE) # 处理NA的情况:NA不算异常值,避免被误删 es_outlier[is.na(x)] = FALSE if(eliminar) { # 返回删除异常值后的向量 return(x[!es_outlier]) } else { # 返回原始向量+异常值标记列 return(data.frame(valor = x, es_outlier = es_outlier)) } }
使用说明
- 直接删除异常值:
# 假设你的数据向量是cepas中的某一列 datos_sin_outliers = detectaYEliminaOutliers(cepas$tu_columna) - 只标记不删除:
datos_con_marcas = detectaYEliminaOutliers(cepas$tu_columna, eliminar = FALSE)
额外提醒
如果你的数据是数据框,想要删除整行异常值,可以结合标记列来过滤:
# 标记数据框中的某列异常值 cepas$es_outlier = detectaYEliminaOutliers(cepas$tu_columna, eliminar = FALSE)$es_outlier # 删除异常值所在行 cepas_sin_outliers = cepas[!cepas$es_outlier, ]
内容的提问来源于stack exchange,提问作者Monse Aleman
相关产品推荐
相关产品推荐

