Сперма, игнорируя NA со сбросом

У меня есть условная сумма со сбросом в ноль.

criteria1 <- c(rep(0,2), rep(1,5), rep(0,3), rep(1,6),rep(0,2))
criteria1[c(6,9,12,13,14,15)] <- NA

#cumsum function, working before the first NA
ave(criteria1, cumsum(criteria1 == 0), FUN = cumsum )
[1]  0  0  1  1  1 NA  1  0 NA  0  1 NA NA NA NA  1  0  0

#and desired output would be
#NA's are replaced with the last value accumulated
#if more than three leave NA's in 
0 0 1 2 3 3 4 0 0 0 1 NA NA NA NA 2 0 0

Некоторые условия:

  • NAs нельзя заменить нулем (или единицей),
  • вектор должен оставаться той же длины (поэтому исключение не вариант)
  • самая длинная длина последовательных игнорируемых NA должна быть равна трем. Если их больше трех, то они должны оставаться как NAs и функция должна продолжаться с последнего не NA.

Некоторые ответы существуют по той же теме, но я не знаю, как собрать все вместе.
Спасибо.


person m_c    schedule 09.02.2017    source источник
comment
Взгляните на ?na.locf из zoo.   -  person ytk    schedule 09.02.2017
comment
что должно произойти, когда есть 4 последовательных значения NA?   -  person Wietze314    schedule 09.02.2017
comment
максимальная длина последовательных игнорируемых NA должна быть равна трем. -- вам, вероятно, следует расширить свой пример, чтобы это условие действительно имело значение.   -  person Frank    schedule 09.02.2017


Ответы (2)


С базой R вы можете: генерировать данные

criteria1 <- c(rep(0,2), rep(1,5), rep(0,3), rep(1,6),rep(0,2))
criteria1[c(6,9,12,13)] <- NA

получить результат

l <- length(criteria1)
cum <- cumsum(ifelse(!is.na(criteria1),criteria1,0))
zero <- which(criteria1 == 0)

res <- cum - rep(cum[zero], c(zero[2:length(zero)],l+1)-zero)

дополнительное решение dplyr:

res <- cum - rep(cum[zero], dplyr::coalesce(dplyr::lead(zero),l+1L)-zero)

обнаруживать и изменять повторы NA > 3 раз

NAs <- rle(is.na(criteria1))
NAloc <- which(NAs$lengths > 3 & NAs$values == 1)
for(i in NAloc)
{
res[seq(sum(NAs$lengths[1:(i-1)])+1,sum(NAs$lengths[1:i]))] <- NA
}
person Wietze314    schedule 09.02.2017
comment
Выглядит хорошо, просто не ломается после достижения ›3 пропущенных значений. - person m_c; 10.02.2017
comment
Вам нужно указать, что вы подразумеваете под «перерывом». Заканчивается ли вектор перед тремя NA? Или что-то другое? - person Wietze314; 10.02.2017

Поскольку NA обрабатываются как нулевые при суммировании, но они сгруппированы так, как если бы они имели то же значение, что и предыдущие значения, вы можете обрабатывать NA по-разному на основе логики в переменной значения и групповой переменной в ave:

library(data.table); library(dplyr); library(zoo);

ave(coalesce(criteria1, 0), rleid(na.locf(criteria1 != 0)), FUN = cumsum)
# [1] 0 0 1 2 3 3 4 0 0 0 1 1 1 2 3 4 0 0
person Psidom    schedule 09.02.2017