【问题标题】:Conditional mean for multiple columns in R?R中多列的条件均值?
【发布时间】:2020-03-02 07:00:40
【问题描述】:

我的数据是这样的:

train <- data.frame(y=c(1,2,1,1), x1=c(2,4,NA,5), x2=c(8,NA,6,12))

我需要用该列的平均值替换每个 x 变量的缺失值 (NA),但必须使用对应 y 值等于行的 y 值的 x 变量的值来计算平均值那个缺失值。

例如:在 x1 列的 NA 所在的行中,y 值等于 1,因此应该将这个缺失值替换为 2 到 5 之间的平均值(即 y 所在的 x1 值还有 1).

我的代码是这样的,但平均值不是有条件的:

for(i in 1:ncol(train)){
  train[is.na(train[,i]), i] <- mean(train[,i], na.rm = TRUE)
}

【问题讨论】:

  • 尝试library(zoo); library(dplyr);train %&gt;% group_by(y) %&gt;% mutate_all(na.aggregate) 对于第 2 行,即 y = 2,'x2' 是 NA,应该保持为 NA

标签: r for-loop mean


【解决方案1】:
library(dplyr)
train %>%
    group_by(y) %>%
    mutate_at(vars(-y), function(v){
        if_else(is.na(v), mean(v, na.rm = TRUE), v)
    }) %>%
    ungroup()
## A tibble: 4 x 3
#      y    x1    x2
#  <dbl> <dbl> <dbl>
#1     1   2       8
#2     2   4     NaN
#3     1   3.5     6
#4     1   5      12

【讨论】:

    【解决方案2】:

    我们可以在按'y'列分组后使用na.aggregate

    library(dplyr)
    library(zoo)
    train %>%
      group_by(y) %>%
       mutate_at(vars(-one_of(group_vars(.))),
                 ~if(all(is.na(.))) NA_real_ else na.aggregate(.))
    # A tibble: 4 x 3
    # Groups:   y [2]
    #      y    x1    x2
    #  <dbl> <dbl> <dbl>
    #1     1   2       8
    #2     2   4      NA
    #3     1   3.5     6
    #4     1   5      12
    

    或者在splitting 数据集之后将na.aggregate 应用到基于'y' 列的data.frames 的list

    train[-1] <- unsplit(lapply(split(train[-1], train$y), na.aggregate), train$y)
    

    【讨论】:

      【解决方案3】:

      考虑ave 是否包含在ifelse 中的分组平均值是否为NA 条件:

      # ITERATE THROUGH ALL COLUMNS BUT FIRST
      for(i in c("x1", "x2")) {    
          train[[i]] <- ifelse(test = is.na(train[[i]]), 
                               yes = ave(train[[i]], train$y, FUN=function(x) mean(x, na.rm=TRUE)), 
                               no = train[[i]])
      }
      
      train   
      #   y  x1  x2
      # 1 1 2.0   8
      # 2 2 4.0 NaN
      # 3 1 3.5   6
      # 4 1 5.0  12
      

      【讨论】:

        猜你喜欢
        • 2018-11-24
        • 2018-08-04
        • 2015-04-11
        • 1970-01-01
        • 2021-07-29
        • 1970-01-01
        • 1970-01-01
        • 2018-11-17
        • 1970-01-01
        相关资源
        最近更新 更多