2

我找到了一些与我正在寻找的答案相似的答案,但代码不起作用。

我需要用 NA 或 NULL 替换每列的所有异常值(根据我们的目的定义为距离平均值超过 2 个 SD)。我试图让这个遍历所有列,计算每列的异常值并替换这些值。

披露:我也知道统计上对去除异常值有强烈的看法,并且使用 SD 作为一种措施来排除它们,因为在这种情况下计算 SD 时包括异常值。这些是我们的统计学家给我的指示,所以我现在正在解决这个问题。

这是我的数据集的一瞥:

data

Group sp.Q13813.SPTN1_HUMAN sp.O14773.TPP1_HUMAN sp.P11137.MTAP2_HUMAN
1 Premutation           10713983468            367492324            2134747097
2 Premutation           10789498495            343303410            2677825476
3 Premutation           11134883489            383589325            2132552280
4 Premutation            9723552595            269965000            2262740921
5 Premutation           11175156282            359864993            1419225650
6 Premutation           10959077349            258095035            3343267633
7 Premutation           10770809133            331554977            2763604046
8 Premutation           11098182537            344384433            2198718886

我尝试了包含 scale() 函数的代码,但是当我执行以下函数时,我发现它替换了列平均值 2 SD 以内的值,并且它使我的代码保持缩放格式。我对这个函数不太熟悉,也不知道如何将它恢复到原始数据点,即使它正在替换正确的异常值。

方法尝试#1

# take note of order for column names
data.names_P <- colnames(data)


# scale all numeric columns
data.numeric.Pre <- select_if(data, is.numeric) %>% # subset of numeric columns
  mutate_all(scale)                             # perform scale separately for each column
data.numeric.Pre[data.numeric.Pre > 2] <- 99999 # set values larger than 2 to NA (none in this example)

# combine results with subset data frame of non-numeric columns
data.Pre <- data.frame(select_if(data, function(x) !is.numeric(x)),
                   data.numeric)

# restore columns to original order
data.Pre <- data.Pre[, data.names_P]

方法尝试#2


FindOutliers <- function(data) {
  upper = (2*sd(data) + mean(data)
  lower = (mean - 2*sd(data))
  result <- which(data < upper | data > lower)
}

我知道第二次尝试不会用 NA 替换数据。

任何帮助将不胜感激。

4

2 回答 2

2

您可以使用一个ifelse函数,这里是一个使用dplyr该函数并将其应用于ifelse包含 term 的所有列的示例HUMAN

library(dplyr)
data %>% mutate_at(.vars = vars(contains("HUMAN")), 
                   .funs= ~ifelse(abs(.)>mean(.)+2*sd(.), NA, .))
于 2020-01-03T01:13:51.480 回答
2

我们可以使用您第二次尝试的函数来替换数据NA

FindOutliers <- function(data) {
   mean_data <- mean(data, na.rm = TRUE)
   sd_data <- sd(data, na.rm = TRUE)
   upper = 2*sd_data + mean_data
   lower = mean_data - 2*sd_data
   replace(data, data > upper | data < lower, NA)
}

library(dplyr)
data %>%  mutate_if(is.numeric, FindOutliers)
#Tested it via
#mtcars %>%  mutate_if(is.numeric, FindOutliers)
于 2020-01-03T01:16:38.120 回答