R - заменить нулевые значения средними ненулевыми для фиксированных категорий - PullRequest
0 голосов
/ 23 марта 2019

Мне дан набор данных следующей формы

year<-rep(c(1990:1999),each=10) 
age<-rep(50:59, 10)
cat1<-rep(c("A","B","C","D","E"),each=100)
value<-rnorm(10*10*5)
value[c(3,51,100,340,441)]<-0
df<-data.frame(year,age,cat1,value)

  year age  cat1     value
1 1990  50    A -0.7941799
2 1990  51    A  0.1592270
3 1990  52    A  0.0000000
4 1990  53    A  1.9222384  
5 1990  54    A  0.3922259
6 1990  55    A -1.2671957

Теперь я хотел бы заменить любые нули в столбце «значение» на среднее значение по столбцу «cat1» ненулевых записей«значение» для соответствующего года и возраста.Например, в 1990 году возраст 52 для cat1 = A равен нулю, его следует заменить на среднее значение ненулевых записей остальных категорий для этого конкретного года и возраста.Поскольку у нас есть

df[df$year==1990 & df$age==52,]
    year age  cat1     value
3   1990  52    A  0.0000000
103 1990  52    B -1.1325446
203 1990  52    C -1.6136773  
303 1990  52    D  0.5724360
403 1990  52    E  0.2795241

, мы заменили бы запись 0 на

sum(df[df$year==1990 & df$age==52,4])/4
[1] -0.4735654

Есть ли хороший и чистый способ для этого вообще?

Ответы [ 2 ]

1 голос
/ 23 марта 2019
library(data.table)
setDT(df)[value==0, value := NA,]
df[, value := replace(value, is.na(value), mean(value, na.rm = TRUE)) , by = .(year, age)]
0 голосов
/ 23 марта 2019

возможно, 99,9% операций с таблицами можно разложить на базовые быстрые и оптимизированные: разбиение, конкатенация (в случае чисел: сумма, умножение и т. Д.), Фильтрация, сортировка, объединение.

Здесь left_join от dplyr - ваш путь. Просто создайте другой фрейм данных, отфильтрованный от нулей и агрегированный по значению с правильной группировкой. Затем замените нули значениями из нового объединенного столбца.

Добро пожаловать на сайт PullRequest, где вы можете задавать вопросы и получать ответы от других членов сообщества.
...