【问题标题】:Filtering , classifying and creating a new variable based on a reference datetime根据参考日期时间过滤、分类和创建新变量
【发布时间】:2021-07-24 02:48:19
【问题描述】:

我目前正在处理一个数据集,其中包含一些供水罐的记录,其中显示了对 5 个不同的罐 (IDENT) 进行技术检查的 DATE 以及TYPE 记录的检查只有两个值:“READ”表示油箱正常工作,“ERROR”表示油箱运行不佳。

IDENT DATE TYPE
X3 30/04/2021 ERROR
X1 1/05/2021 READ
X1 2/05/2021 ERROR
X4 3/05/2021 READ
X9 4/05/2021 ERROR
X6 5/05/2021 READ
X1 6/05/2021 READ
X3 7/05/2021 ERROR
X3 8/05/2021 READ

我必须为每个水箱创建一个可以过滤和选择每个 TYPE="ERROR" DATE 的数据框(指定水箱的日期集上是否没有记录错误是没有必要的显示它)并显示每个坦克的错误之前的最新TYPE="READ" DATE以及每个坦克的错误日期之后的最新DATE,以说明我要实现这张表:

| IDENT | READ_PRIOR |    ERROR   | POST_READ |
|:-----:|:----------:|:----------:|:---------:|
|   X3  |     NA     | 30/04/2021 | 8/05/2021 |
|   X3  |     NA     |  7/05/2021 | 8/05/2021 |
|   X1  |  1/05/2021 |  2/05/2021 | 6/05/2021 |
|   X9  |     NA     |  4/05/2021 |     NA    |

我尝试了什么?

我已经开始解决这个问题,方法是按日期按时间顺序排列数据集,并使用 tidyverse 包按 IDENT 分组,我也可以使用 top_n 函数为组选择最新的日期,但我的问题是我似乎无法找到一种方法来成功过滤或选择参考 TYPE="ERROR" 之前和之后的坦克的最新日期,所以这就是我头疼的地方。非常感谢你帮我找到我真正感激的人。

代码:

df<- tibble::tribble(
~IDENT  ~DATE   ~TYPE,
        
"X3",   "30/04/2021",   "ERROR",
        
"X1",   "1/05/2021",    "READ",
        
"X1",   "2/05/2021",    "ERROR",
        
"X4",   "3/05/2021",    "READ",
        
"X9",   "4/05/2021",    "ERROR",
        
"X6",   "5/05/2021",    "READ",
        
"X1",   "6/05/2021",    "READ",
        
"X3",   "7/05/2021",    "ERROR",
        
"X3",   "8/05/2021",    "READ")
        

非常感谢你们!

【问题讨论】:

    标签: r date filtering tidyverse data-wrangling


    【解决方案1】:

    我们将 'DATE' 列转换为 Date 类(dmy - 来自 lubridate),arrange 按 'IDENT' 和 'DATE' 的行,按 'IDENT' 分组,重新编码 'READ' 值'READ_PRIOR' 和 'POST_READ' 与 case_when 基于 'ERROR' 的存在,删除 'TYPE' 中没有 'ERROR' 值的 'IDENT' 组,使用pivot_wider 重塑为 'wide' 格式和fill 'POST_READ' 中的值与每个 'IDENT' 的非 NA 相邻值

    library(dplyr)
    library(tidyr)
    library(data.table)
    library(lubridate)
    df %>% 
      mutate(DATE = dmy(DATE)) %>%
      arrange(IDENT, DATE) %>% 
      group_by(IDENT) %>% 
      mutate(TYPE = case_when(TYPE == 'READ' & lead(TYPE) == 'ERROR' 
         ~ 'READ_PRIOR', TYPE == 'READ' ~ 'POST_READ', TRUE ~ TYPE)) %>%       
      filter('ERROR' %in% TYPE) %>%     
      mutate(rn = rowid(IDENT, TYPE)) %>% 
      pivot_wider(names_from = TYPE, values_from = DATE) %>% 
      fill(POST_READ) %>%
      ungroup %>%
      select(-rn)
    

    -输出

    # A tibble: 4 x 4
    #  IDENT READ_PRIOR ERROR      POST_READ 
    #  <chr> <date>     <date>     <date>    
    #1 X1    2021-05-01 2021-05-02 2021-05-06
    #2 X3    NA         2021-04-30 2021-05-08
    #3 X3    NA         2021-05-07 2021-05-08
    #4 X9    NA         2021-05-04 NA        
    

    【讨论】:

    • 太棒了! 10/10 我喜欢你的代码如此干净的方式..感谢一开始的解释......我有一个问题(我正在学习 R)你正在使用库 data.table 哪些函数完全依赖于这个库你用的代码?再次非常感谢非常感谢
    • @R_Student 它只是rowid。如果您不想依赖,请使用group_by(IDENT, TYPE) %&gt;% mutate(rn = row_number()) %&gt;%
    猜你喜欢
    • 1970-01-01
    • 2022-12-21
    • 1970-01-01
    • 2021-07-24
    • 2020-04-06
    • 1970-01-01
    • 1970-01-01
    • 1970-01-01
    • 2018-07-25
    相关资源
    最近更新 更多