【问题标题】:Find the maximum value within a range of dates with dplyr in R在 R 中使用 dplyr 查找日期范围内的最大值
【发布时间】:2020-08-21 04:56:44
【问题描述】:

这听起来像是一个愚蠢的问题,但我在网上找不到答案。我有一个大型数据集,如下所示:

set.seed(1)
df <- data.frame(date = as.Date("2010-01-01")+seq(0,729), value = rnorm(730)) 

我想使用dplyr 查找从每个日期开始的 1 年窗口(加/减)内的滚动最大值。例如,对于日期“2010-05-01”,我想在“2009-05-01”和“2011-05-01”之间找到最大值。 max_value 应该在 df 的新列中。谢谢。

【问题讨论】:

  • 在问题中设置你的种子,以便它可以重现。 set.seed(1)(或任何其他号码都可以)
  • 操作,我忘了set.seed!干得好!谢谢!
  • 使用 data.table 可能更容易:它绝对应该是 dplyr 吗?

标签: r dplyr max


【解决方案1】:

slidertidyverse 的一部分。

试试这个:

library(dplyr)
library(slider)
df %>% mutate(two_years_max = slide_index_dbl(value, date, max, .before = 365, .after = 365))

【讨论】:

    【解决方案2】:

    这可能是您正在寻找的:

    library(tidyverse)
    set.seed(1)
    df <- data.frame(date = as.Date("2010-01-01")+seq(0,729), value = rnorm(730)) 
    
    df %>% as_tibble() %>%
      dplyr::mutate(previous = max(lag(value, order_by = date,n = 365), na.rm = T),
                    nexts = max(lead(value, order_by = date,n = 365), na.rm = T),
                    max_value = max(previous, nexts)) 
    #> # A tibble: 730 x 5
    #>    date        value previous nexts max_value
    #>    <date>      <dbl>    <dbl> <dbl>     <dbl>
    #>  1 2010-01-01 -0.626     2.65  3.81      3.81
    #>  2 2010-01-02  0.184     2.65  3.81      3.81
    #>  3 2010-01-03 -0.836     2.65  3.81      3.81
    #>  4 2010-01-04  1.60      2.65  3.81      3.81
    #>  5 2010-01-05  0.330     2.65  3.81      3.81
    #>  6 2010-01-06 -0.820     2.65  3.81      3.81
    #>  7 2010-01-07  0.487     2.65  3.81      3.81
    #>  8 2010-01-08  0.738     2.65  3.81      3.81
    #>  9 2010-01-09  0.576     2.65  3.81      3.81
    #> 10 2010-01-10 -0.305     2.65  3.81      3.81
    #> # ... with 720 more rows
    

    reprex package (v0.3.0) 于 2020-08-20 创建

    【讨论】:

    • 嗨,我喜欢这种 dplyr 方法,但我得到了另一个结果。第一行的max_value 应该是max(df$value[df$date &lt;= as.Date("2010-01-01")+365 &amp; df$date &gt;= as.Date("2010-01-01")-365]) [1] 2.649167
    • 同意!好收获
    【解决方案3】:

    不是最优雅的,但它会起作用。

    set.seed(1)
    df <- data.frame(date = as.Date("2010-01-01")+seq(0,729), value = rnorm(730)) 
    
    for(i in 1:nrow(df)){
      tmp <- df %>%
        filter(date >= df[i,'date'] - 365, date <= df[i,'date'] + 365) %>% 
        summarise(value = max(value)) %>%
        pull()
      
      df[i,'max_value'] <- tmp
    }
    
            date      value max_value
    1 2010-01-01 -0.6264538  2.649167
    2 2010-01-02  0.1836433  2.649167
    3 2010-01-03 -0.8356286  2.649167
    4 2010-01-04  1.5952808  2.649167
    5 2010-01-05  0.3295078  2.649167
    6 2010-01-06 -0.8204684  2.649167
    

    【讨论】:

    • 这很好用,但有没有完整的dplyr 方法?因为这是更长的pipe 的一部分...非常感谢!
    【解决方案4】:

    你可以使用zoo::rollmax:

    df %>% 
      mutate(rollmax = zoo::rollmax(value, 720, align = "center", 
                                    fill = c("extend", NA, "extend")))
    

    您可以更改fill 参数,以决定当您没有完整的滚动两年到最大值时您想要在第一年和最后一年的数据中做什么。 (在你的例子中你只有两年,所以只有一天符合“两边一年”的规定)

    【讨论】:

    • 嗨,zoo 很好,我没想到。但是,第一行中的max_value 应该是max(df$value[df$date &lt;= as.Date("2010-01-01")+365 &amp; df$date &gt;= as.Date("2010-01-01")-365]) [1] 2.649167,而你得到的是3.810277
    猜你喜欢
    • 1970-01-01
    • 1970-01-01
    • 1970-01-01
    • 1970-01-01
    • 1970-01-01
    • 1970-01-01
    • 1970-01-01
    • 1970-01-01
    • 2016-12-08
    相关资源
    最近更新 更多