我有一个数据集,参与者被分配到不同的小组并完成了相同的测试。我知道我可以使用聚合函数来识别均值和标准差,但我无法弄清楚如何找到这些组中的离群值。
df<-read.table(header=T, text="id, group, test1, test2
1, 0, 57, 82
2, 0, 77, 80
3, 0, 67, 90
4, 0, 15, 70
5, 0, 58, 72
6, 1, 18, 44
7, 1, 44, 44
8, 1, 18, 46
9, 1, 20, 44
10, 1, 14, 38")
我喜欢这段代码的格式,但是不知道如何更改它,以便为每个测试的每个组识别异常值。
还,我希望将异常值视为大于2个标准偏差,而不是3个标准偏差。我可以在此代码中对其进行格式化吗?
##to get outliers on test1 if groups were combined
badexample <- boxplot(df$test1, plot=F)$out
which(df$test1 %in% badexample)
如果我想将两个组的异常值一起放在test1上,但我想按组分开,则可以使用。
输出应包含: test1上第0组的离群值 test2上第0组的异常值 测试1上第1组的异常值 test2上第1组的异常值
答案 0 :(得分:1)
您可以编写函数来计算离群值,然后使用ave
进行调用。
outlier <- function(x, SD = 2){
mu <- mean(x)
sigma <- sd(x)
out <- x < mu - SD*sigma | x > mu + SD*sigma
out
}
with(df, ave(test1, group, FUN = outlier))
# [1] 0 0 0 0 0 0 0 0 0 0
with(df, ave(test2, group, FUN = outlier))
# [1] 0 0 0 0 0 0 0 0 0 0
要在df
中具有这些结果的新列,请按常规方式分配。
df$out1 <- with(df, ave(test1, group, FUN = outlier))
df$out2 <- with(df, ave(test2, group, FUN = outlier))
答案 1 :(得分:0)
使用data.table
的选项:
library(data.table)
df <- read.table(header=T, sep=",", text="id, group, test1, test2
1, 0, 57, 82
2, 0, 77, 80
3, 0, 67, 90
4, 0, 15, 70
5, 0, 58, 72
6, 1, 18, 44
7, 1, 44, 44
8, 1, 18, 46
9, 1, 20, 44
10, 1, 14, 38")
DT <- as.data.table(df)
DT[, `:=`(mean1 = mean(test1), sd1 = sd(test1), mean2 = mean(test2), sd2 = sd(test2)), by = "group"]
DT[, `:=`(outlier1 = abs(test1-mean1)>2*sd1, outlier2 = abs(test2-mean2)>2*sd2)]
DT
# id group test1 test2 mean1 sd1 mean2 sd2 outlier1 outlier2
# 1: 1 0 57 82 54.8 23.66854 78.8 8.074652 FALSE FALSE
# 2: 2 0 77 80 54.8 23.66854 78.8 8.074652 FALSE FALSE
# 3: 3 0 67 90 54.8 23.66854 78.8 8.074652 FALSE FALSE
# 4: 4 0 15 70 54.8 23.66854 78.8 8.074652 FALSE FALSE
# 5: 5 0 58 72 54.8 23.66854 78.8 8.074652 FALSE FALSE
# 6: 6 1 18 44 22.8 12.04990 43.2 3.033150 FALSE FALSE
# 7: 7 1 44 44 22.8 12.04990 43.2 3.033150 FALSE FALSE
# 8: 8 1 18 46 22.8 12.04990 43.2 3.033150 FALSE FALSE
# 9: 9 1 20 44 22.8 12.04990 43.2 3.033150 FALSE FALSE
# 10: 10 1 14 38 22.8 12.04990 43.2 3.033150 FALSE FALSE
答案 2 :(得分:0)
这里是dplyr
的一种方式-
df %>%
mutate_at(
vars(starts_with("test")),
list(outlier = ~(abs(. - mean(.)) > 2*sd(.)))
)
id group test1 test2 test1_outlier test2_outlier
1 1 0 57 82 FALSE FALSE
2 2 0 77 80 FALSE FALSE
3 3 0 67 90 FALSE FALSE
4 4 0 15 70 FALSE FALSE
5 5 0 58 72 FALSE FALSE
6 6 1 18 44 FALSE FALSE
7 7 1 44 44 FALSE FALSE
8 8 1 18 46 FALSE FALSE
9 9 1 20 44 FALSE FALSE
10 10 1 14 38 FALSE FALSE