Отставание в R, когда условие соответствует - PullRequest
1 голос
/ 25 января 2020

У меня есть фрейм данных только с датами медицинских осмотров и наличием инфекции (да / нет), и я хочу добавить третий столбец, представляющий дату последней инфекции. Новый столбец last_infection должен иметь NA, если у пациента ранее не было инфекции. Если у них была предыдущая инфекция, она должна показать дату самого последнего посещения, где они проверили «да» на наличие инфекции.

Я хочу, чтобы результат выглядел так:

date      infection   last_infection
01-01-18  no          NA
06-01-18  no          NA
07-01-18  yes         NA
09-01-18  no          07-01-18
01-01-19  no          07-01-18
02-01-19  yes         07-01-18
03-01-19  yes         02-01-19
04-01-19  no          03-01-19
05-01-19  no          03-01-19

Как я могу сделать это в R? Может ли такая функция, как lag() проверить состояние, или я должен сделать что-то еще полностью?

Ответы [ 2 ]

2 голосов
/ 26 января 2020

Я бы предложил что-то вроде этого. Нет смысла использовать cumsum или группировки, если вы используете fill из пакета tidyr.

library(tidyverse)

df %>% 
  mutate(
    last_infection = if_else(lag(infection) == "yes", lag(date), NA_character_)
  ) %>% 
  fill(last_infection)
#> # A tibble: 9 x 3
#>   date     infection last_infection
#>   <chr>    <chr>     <chr>         
#> 1 01-01-18 no        <NA>          
#> 2 06-01-18 no        <NA>          
#> 3 07-01-18 yes       <NA>          
#> 4 09-01-18 no        07-01-18      
#> 5 01-01-19 no        07-01-18      
#> 6 02-01-19 yes       07-01-18      
#> 7 03-01-19 yes       02-01-19      
#> 8 04-01-19 no        03-01-19      
#> 9 05-01-19 no        03-01-19

Создано в 2020-01-25 пакетом Представлять (v0.3.0)

0 голосов
/ 25 января 2020

Мы можем создать переменную группировки на основе логического вектора, созданного с помощью «инфекции», и использовать его для lag столбца. Здесь мы загружаем только dplyr, а не любые другие пакеты

library(dplyr)
df1 %>%
   group_by(grp = cumsum(infection == "yes")) %>%
   mutate(new = first(date)) %>%
   ungroup %>%
   mutate(new = replace(lag(new), seq_len(match(1, grp)), NA)) %>%
   select(-grp)
# A tibble: 9 x 4
#  date     infection last_infection new     
#  <chr>    <chr>     <chr>          <chr>   
#1 01-01-18 no        <NA>           <NA>    
#2 06-01-18 no        <NA>           <NA>    
#3 07-01-18 yes       <NA>           <NA>    
#4 09-01-18 no        07-01-18       07-01-18
#5 01-01-19 no        07-01-18       07-01-18
#6 02-01-19 yes       07-01-18       07-01-18
#7 03-01-19 yes       02-01-19       02-01-19
#8 04-01-19 no        03-01-19       03-01-19
#9 05-01-19 no        03-01-19       03-01-19

data

df1 <- structure(list(date = c("01-01-18", "06-01-18", "07-01-18", "09-01-18", 
"01-01-19", "02-01-19", "03-01-19", "04-01-19", "05-01-19"), 
    infection = c("no", "no", "yes", "no", "no", "yes", "yes", 
    "no", "no"), last_infection = c(NA, NA, NA, "07-01-18", "07-01-18", 
    "07-01-18", "02-01-19", "03-01-19", "03-01-19")),
    class = "data.frame", row.names = c(NA, 
-9L))
...