从数据帧中删除单变量异常值(+ -3 SD)

luk*_*123 4 r outliers

我对R很陌生,以至于我无法在其他人的问题中找到我需要的东西.我认为我的问题非常简单,没有其他人费心去问它.

什么是最简单的代码来创建一个新的数据框,它排除了单变量异常值的数据(我将它们定义为从它们的条件的平均值为3个SD的点),在它们的条件下,在某个变量上?

我很尴尬地展示我尝试过的东西,但现在却是

greaterthan <- mean(dat$var2[dat$condition=="one"]) + 
               2.5*(sd(dat$var2[dat$condition=="one"]))
lessthan    <- mean(dat$var2[dat$condition=="one"]) -
               2.5*(sd(dat$var2[dat$condition=="one"]))   

withoutliersremovedone1 <-dat$var2[dat$condition=="one"] < greaterthan
Run Code Online (Sandbox Code Playgroud)

而我几乎已经被困在那里了.

谢谢

the*_*ail 7

> dat <- data.frame(
                    var1=sample(letters[1:2],10,replace=TRUE),
                    var2=c(1,2,3,1,2,3,102,3,1,2)
                   )
> dat
   var1 var2
1     b    1
2     a    2
3     a    3
4     a    1
5     b    2
6     b    3
7     a  102 #outlier
8     b    3
9     b    1
10    a    2
Run Code Online (Sandbox Code Playgroud)

现在只返回那些不是(!)大于2 absolute sd的行mean.很明显,sd你想要成为截止日期的2.

> dat[!(abs(dat$var2 - mean(dat$var2))/sd(dat$var2)) > 2,]
   var1 var2
1     b    1
2     a    2
3     a    3
4     a    1
5     b    2
6     b    3 # no outlier
8     b    3 # between here
9     b    1
10    a    2
Run Code Online (Sandbox Code Playgroud)

或者更简单的使用scale功能:

dat[!abs(scale(dat$var2)) > 2,]

   var1 var2
1     b    1
2     a    2
3     a    3
4     a    1
5     b    2
6     b    3
8     b    3
9     b    1
10    a    2
Run Code Online (Sandbox Code Playgroud)

编辑

这可以扩展到使用组内查找 by

do.call(rbind,by(dat,dat$var1,function(x) x[!abs(scale(x$var2)) > 2,] ))
Run Code Online (Sandbox Code Playgroud)

这假定dat$var1是您定义每行所属的组的变量.