在R中绘制箱线图+带状图时,如何排除带状图的异常值
解决stripchart排除箱线图异常值的问题
我明白你现在的困扰——用基础R绘制箱线图+带状图组合时,异常值被重复绘制:箱线图的黑色空心点和带状图的蓝色圆点重叠,导致画面杂乱。其实stripchart本身并没有内置参数直接识别并排除箱线图定义的异常值,但我们可以通过两种方法实现需求:
方法一:提取箱线图阈值,过滤数据后绘制stripchart
这是最稳妥的方案,先从箱线图的统计结果里拿到异常值的判定边界,再过滤掉超出边界的数据,最后用过滤后的数据画带状图。
步骤1:绘制箱线图并保存统计结果
运行boxplot时把返回对象保存下来,这个对象里包含了每个组的上下须(也就是异常值的判定边界):
# 假设xx是你的导入数据集,先绘制箱线图并保存结果 bp <- boxplot(xx, lwd = 1.5, ylab = 'Minutes', xlab = "Epoch")
步骤2:过滤掉异常值
针对每个Epoch组(数据框的每一列),保留落在上下须范围内的值:
# 遍历每一列,过滤超出上下须范围的数值 filtered_xx <- lapply(seq_along(xx), function(i) { lower_bound <- bp$stats[1, i] # 第1个统计值是下须位置 upper_bound <- bp$stats[5, i] # 第5个统计值是上须位置 xx[[i]][xx[[i]] >= lower_bound & xx[[i]] <= upper_bound] }) # 把过滤后的列表转回数据框,恢复原列名 filtered_xx <- as.data.frame(filtered_xx) colnames(filtered_xx) <- colnames(xx)
步骤3:绘制过滤后的带状图
用过滤后的数据叠加在箱线图上:
stripchart(filtered_xx, vertical = TRUE, method = "jitter", add = TRUE, pch = 20, col = 'blue')
这样带状图就只会显示箱线图上下须内的数值,异常值仅保留箱线图的黑色空心点,不会重复绘制。
方法二:视觉技巧(无需修改数据)
如果你不想改动原始数据,可以通过调整箱线图异常值的样式,让它覆盖在带状图的蓝色点上,快速实现视觉上的“只保留箱线图异常值”:
# 绘制箱线图时,把异常值设为黑色空心点(和背景区分开,同时覆盖下方蓝色点) boxplot(xx, lwd = 1.5, ylab = 'Minutes', xlab = "Epoch", outcol = "black", outpch = 1) # 正常绘制带状图 stripchart(xx, vertical = TRUE, method = "jitter", add = TRUE, pch = 20, col = 'blue')
不过这个方法的局限性是:如果带状图的点和异常值位置完全重合,可能还是会有轻微重叠,所以更推荐第一种过滤数据的方案。
解释你之前遇到的错误
ylim参数错误:你写的ylim (0,20)是语法错误,正确写法是ylim = c(0,20),而且true要大写为TRUE。但这个参数只是限制Y轴范围,超出范围的点会被截断,并非真正排除异常值。outcol参数无效:stripchart本身没有识别异常值的逻辑,所以它不支持outcol这类针对异常值的参数,自然会提示“不是图形参数”。
内容的提问来源于stack exchange,提问作者Ausfernan




