Как отобразить средние результаты вменения из обучающего набора в тестовый набор?

У меня есть вектор:

mean_imputed_values_trainining_set <- c(0.5247570, 0.4077914,0.1393320,0.8233340, 0.3610365,0.1805526, 0.2375011, 9.8848462 )      

Я попытался создать настраиваемую функцию, в которой результаты вектора будут вменять значения NA. Первый элемент вектора соответствует первому столбцу фрейма данных. Вот пользовательская функция:

NA_imputer_test <- function(train, test) {

  map_df(train, function(x) {

    map_df(test, function(element) {

      if(is.numeric(element)) {
        ifelse(is.na(element), mean(x, na.rm = TRUE), element) 
      } else { 
        element 
      }
    })
  }) 


}  

test_set <- NA_imputer_test(train, test)

Однако когда я пытаюсь использовать настраиваемую функцию, я не могу использовать результаты вектора. Вместо этого только значение 0,5247570 подставляет все пропущенные значения.

Как я могу убедиться, что каждый элемент вектора соответствует каждому элементу фрейма данных?

Я знаю, что есть решения с MICE и подобными библиотеками, но я пытаюсь сделать свою функцию.

1 ответ

Решение

Надеюсь, это даст вам то, что вы хотите. Я создам образец фрейма данных.

df <- data.frame(matrix(data = sample(100,80,replace=TRUE), ncol = 8))
df[df>80] <- NA_integer_

> df

   X1 X2 X3 X4 X5 X6 X7 X8
1  80 14 NA 78 39 60 14 25
2  75 46  4 47 61 74 36 NA
3  67  2  2 NA 42 NA NA NA
4   8 34 15  9 NA 79 62  9
5  NA 34 10 NA NA  5 42 NA
6  NA 75 17  3  8 45 72 45
7  71 64 NA NA NA 77 20 63
8  25 NA 24 58 NA NA 47 NA
9  80 71 NA  3 71 22 NA 64
10 43 43 NA NA 54 73 55 77

Теперь, если вы хотите убедиться, что каждый элемент вектора соответствует каждому элементу фрейма данных, так что первый элемент вектора соответствует первому столбцу фрейма данных., то вы знаете, что столбцы числовые, поэтомуif(is.numeric(element))может не понадобиться. Ты можешь использоватьpurrr::map сюда:

> map2_dfr(df, mean_imputed_values_trainining_set,
+          ~ replace(.x, is.na(.x), .y))

# A tibble: 10 x 8
       X1     X2     X3     X4     X5     X6     X7    X8
    <dbl>  <dbl>  <dbl>  <dbl>  <dbl>  <dbl>  <dbl> <dbl>
 1 80     14      0.139 78     39     60     14     25   
 2 75     46      4     47     61     74     36      9.88
 3 67      2      2      0.823 42      0.181  0.238  9.88
 4  8     34     15      9      0.361 79     62      9   
 5  0.525 34     10      0.823  0.361  5     42      9.88
 6  0.525 75     17      3      8     45     72     45   
 7 71     64      0.139  0.823  0.361 77     20     63   
 8 25      0.408 24     58      0.361  0.181 47      9.88
 9 80     71      0.139  3     71     22      0.238 64   
10 43     43      0.139  0.823 54     73     55     77   

Однако, если вы хотите вменять средние значения числовых столбцов в ваших данных, сделайте следующее:

# Adding a non-numeric column 
> df[,'X9'] <- sample(letters, 10, replace=T)


> map_if(df, is.numeric, 
+        function(x) replace(x, is.na(x), mean(x, na.rm=T)), 
+        .else = function(x) x)%>%bind_cols()

# A tibble: 10 x 9
      X1    X2    X3    X4    X5    X6    X7    X8 X9   
   <dbl> <dbl> <dbl> <dbl> <dbl> <dbl> <dbl> <dbl> <chr>
 1  80    14      12    78  39    60    14    25   d    
 2  75    46       4    47  61    74    36    47.2 w    
 3  67     2       2    33  42    54.4  43.5  47.2 n    
 4   8    34      15     9  45.8  79    62     9   r    
 5  56.1  34      10    33  45.8   5    42    47.2 g    
 6  56.1  75      17     3   8    45    72    45   y    
 7  71    64      12    33  45.8  77    20    63   t    
 8  25    42.6    24    58  45.8  54.4  47    47.2 d    
 9  80    71      12     3  71    22    43.5  64   d    
10  43    43      12    33  54    73    55    77   m    

Вы можете обернуть это функцией:

NA_imputer_test <- function(data){
  out_df = map_if(data, is.numeric, 
                  function(x) replace(x, is.na(x), mean(x, na.rm=T)), 
                  .else = function(x) x)%>%bind_cols()
  return(out_df)
}
Другие вопросы по тегам