Как правильно пометить конец первой последовательности группы? - PullRequest
1 голос
/ 15 февраля 2020

Это пример типа используемого фрейма данных и желаемого вывода столбца.

reprEx <- data.frame(id = c(1,1,1,1,1,1,1,2,2,2,2,3,3,3),
             stage1 = c("open","open","open","approved","approved","open","declined","open","open","open","declined","open","approved","declined"))

Desireddf <- data.frame(id = c(1,1,1,1,1,1,1,2,2,2,2,3,3,3),
             stage1 = c("open","open","open","approved","approved","open","declined","open","open","open","declined","open","approved","declined"),
             desiredResult = c(0,0,1,1,0,0,1,0,0,1,1,1,1,1))

Я пытаюсь использовать dplyr для правильной пометки при каждом изменении этапа внутри сгруппированного идентификатора. , Подтвержденные и отклоненные флаги просты, потому что мне нужно только отметить первый случай отклоненного или утвержденного появления с:

    reprExWrong <- reprEx %>% group_by(id,stage1) %>%
  mutate(desiredResult = ifelse(stage1 == last(stage1) & stage1 == "open",1,
                                ifelse(stage1 == first(stage1) & stage1 %in% c("approved","declined"),1,0)
                                )
  )

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

reprExWrong <- data.frame(id = c(1,1,1,1,1,1,1,2,2,2,2,3,3,3),
             stage1 = c("open","open","open","approved","approved","open","declined","open","open","open","declined","open","approved","declined"),
             notdesiredResult = c(0,0,0,1,0,1,1,0,0,1,1,1,1,1))

В этом случае внутри id1 мне понадобится флаг, чтобы показать, где последовательность достигает последнего открытия до появления одобренного, а не в открытии после появления одобренного. Мне нужен только флаг в строке последнего вхождения open, если эта последовательность открытий является первой последовательностью внутри идентификатора. Извините за путаницу, я был бы рад уточнить. Это просто для правильного определения сценических переходов для целей записи

Ответы [ 3 ]

1 голос
/ 15 февраля 2020
reprEx %>% group_by(id) %>% mutate(lastopen=cumsum(lead(stage1!="open"))==1)

То, что это делает, проверяет первый раз, когда stage1 НЕ "открыт" в группе идентификаторов, и устанавливает строку перед этим как TRUE. Результат:

# A tibble: 14 x 3
# Groups:   id [3]
      id stage1   lastopen
   <dbl> <fct>    <lgl>   
 1     1 open     FALSE   
 2     1 open     FALSE   
 3     1 open     TRUE    
 4     1 approved FALSE   
 5     1 approved FALSE   
 6     1 open     FALSE   
 7     1 declined NA      
 8     2 open     FALSE   
 9     2 open     FALSE   
10     2 open     TRUE    
11     2 declined NA      
12     3 open     TRUE    
13     3 approved FALSE   
14     3 declined NA   

Если есть проблемы с NA, вы также можете добавить:

%>% mutate(lastopen=ifelse(is.na(lastopen),FALSE,lastopen))

# A tibble: 14 x 3
# Groups:   id [3]
      id stage1   lastopen
   <dbl> <fct>    <lgl>   
 1     1 open     FALSE   
 2     1 open     FALSE   
 3     1 open     TRUE    
 4     1 approved FALSE   
 5     1 approved FALSE   
 6     1 open     FALSE   
 7     1 declined FALSE   
 8     2 open     FALSE   
 9     2 open     FALSE   
10     2 open     TRUE    
11     2 declined FALSE   
12     3 open     TRUE    
13     3 approved FALSE   
14     3 declined FALSE 
1 голос
/ 15 февраля 2020

Попробуйте это:

reprEx %>% 
  group_by(id) %>%
  mutate(result = stage1 != lag(stage1), 
         result = ifelse(is.na(result), 0, result))
1 голос
/ 15 февраля 2020

Конечно, есть что-то менее запутанное, но это, вероятно, сработает:

library(dplyr)

reprEx %>%
  group_by(id) %>%
  mutate(idx = cumsum(stage1 != lag(stage1, default = first(stage1))),
         desiredResult = case_when(
           idx != lag(idx, default = first(idx)) & stage1 != 'open' ~ 1,
           lead(idx, default = last(idx)) != idx & stage1 == 'open' & idx == min(idx[stage1 == 'open']) ~ 1,
           TRUE ~ 0
         ),
         idx = NULL
  )

Вывод:

   id   stage1 desiredResult
1   1     open             0
2   1     open             0
3   1     open             1
4   1 approved             1
5   1 approved             0
6   1     open             0
7   1 declined             1
8   2     open             0
9   2     open             0
10  2     open             1
11  2 declined             1
12  3     open             1
13  3 approved             1
14  3 declined             1
Добро пожаловать на сайт PullRequest, где вы можете задавать вопросы и получать ответы от других членов сообщества.
...