【问题标题】:R function for different follow-up intervals + lubridate不同随访间隔的 R 功能 + lubridate
【发布时间】:2022-01-11 19:09:39
【问题描述】:

我有以下df:

df = data.frame(id=c(1,1,1,1,1,1),
                date=c(as.Date("2000-01-01"), as.Date("2000-07-11"),
                       as.Date("2000-08-01"), as.Date("2000-12-31"),
                       as.Date("2002-05-04"), as.Date("2002-06-01")))

我需要以下结果:


result = data.frame(id=c(1,1,1,1,1,1),
                date=c(as.Date("2000-01-01"), as.Date("2000-07-11"),
                       as.Date("2000-08-01"), as.Date("2000-12-31"),
                       as.Date("2002-05-04"), as.Date("2002-06-01")),
                days_91 = c(0,0,1,0,0,1),
                days_182 = c(0,0,1,0,0,1),
                days_273 = c(0,1,1,1,0,1),
                days_365 = c(0,1,1,1,0,1))

基本上,对于某个日期,我想知道在过去 X 天内是否存在同一个 ID 的先前日期。

我认为一定存在润滑功能,但没有找到。

结果:

id date days_91 days_182 days_273 days_365
1 2000-01-01 0 0 0 0
1 2000-07-11 0 0 1 1
1 2000-08-01 1 1 1 1
1 2000-12-31 0 1 1 1
1 2002-05-04 0 0 0 0
1 2002-06-01 1 1 1 1

例如,对于第 3 行,在过去 91、182、273 和 365 天中存在上一个日期。但是在第 2 行中,过去 91 天和 182 天没有以前的访问

【问题讨论】:

    标签: r date lubridate


    【解决方案1】:

    这是另一个使用map2map_dfc 的选项,来自purrr。在提供给定的date 和之前的date(按排序顺序)后,您可以将这两个值的差异与数字向量中的所有元素(包含天数,例如 91、182 等)进行比较.

    library(tidyverse)
    
    my_days <- c(91, 182, 273, 365)
    
    df %>%
      group_by(id) %>%
      arrange(date, .by_group = T) %>%
      mutate(days = map2(
        date,
        lag(date, default = as.Date(-Inf)),
        \(x, y) {
          bind_cols(map_dfc(set_names(my_days, paste0("days_", my_days)), ~+(x - y < .x)))
        }
      )) %>%
      unnest(days)
    

    输出

         id date       days_91 days_182 days_273 days_365
      <dbl> <date>       <int>    <int>    <int>    <int>
    1     1 2000-01-01       0        0        0        0
    2     1 2000-07-11       0        0        1        1
    3     1 2000-08-01       1        1        1        1
    4     1 2000-12-31       0        1        1        1
    5     1 2002-05-04       0        0        0        0
    6     1 2002-06-01       1        1        1        1
    

    【讨论】:

      【解决方案2】:

      我们可以使用 dplyr 遍历您要检查的日期列表,如果“日期”列中的任何日期在前 x 天内存在,则将返回 1:

      library(dplyr)
      
      dates_check <- c(91, 192, 213, 365) # Dates we want to check
      
      prev_dates <- function(prev_date){
        colname <- paste('days_', prev_date, sep='') # Dynamically create the column name
        df <<- df %>%
          group_by(id) %>% # Group our data by id
          rowwise() %>% # Perform rowwise operation
          mutate(!!colname := as.integer(any(df$date > date - prev_date & df$date < date))) 
      }
      
      
      lapply(dates_check, prev_dates)
      
      # A tibble: 6 x 6
      # Rowwise:  id
           id date       days_91 days_182 days_273 days_365
        <dbl> <date>       <int>    <int>    <int>    <int>
      1     1 2000-01-01       0        0        0        0
      2     1 2000-07-11       0        0        1        1
      3     1 2000-08-01       1        1        1        1
      4     1 2000-12-31       0        1        1        1
      5     1 2002-05-04       0        0        0        0
      6     1 2002-06-01       1        1        1        1
      

      【讨论】:

      • 我已经澄清了文字
      • 谢谢,澄清帮助。我已经更新了答案。
      猜你喜欢
      • 1970-01-01
      • 1970-01-01
      • 2022-10-05
      • 2021-08-07
      • 1970-01-01
      • 1970-01-01
      • 1970-01-01
      • 1970-01-01
      • 2013-02-19
      相关资源
      最近更新 更多