【问题标题】:Writing a function in R to iteratively subset dataframe by time在R中编写一个函数以按时间迭代地子集数据帧
【发布时间】:2019-05-26 16:17:54
【问题描述】:

我正在处理一个包含跨时间案例的数据框,比如说 10/01/18-12/31/18。目前,我编写了一个脚本,允许我按日期对数据进行子集化,并且需要手动输入特定日期。这是带有虚拟数据集的脚本:

> mydata
                  date dummy
1  2018-10-01 21:41:00     A
2  2018-10-03 21:41:00     B
3  2018-10-12 21:41:00     C
4  2018-11-01 21:41:00     D
5  2018-11-02 21:41:00     E
6  2018-11-12 21:41:00     F
7  2018-11-15 21:41:00     G
8  2018-12-02 21:41:00     H
9  2018-12-07 21:41:00     I
10 2018-12-12 21:41:00     J

#put date into readable format
mydata$date <- as.POSIXct(mydata$date, format="%m/%d/%y %H:%M") 

# TOCHANGE: Adjust time points accordingly.
t1 = mydata[mydata$date >= "2018-10-01" & mydata$date <= "2018-10-31",]  
t2 = mydata[mydata$date >= "2018-11-01" & mydata$date <= "2018-11-30",]  
t3 = mydata[mydata$date >= "2018-12-01" & mydata$date <= "2018-12-30",]  

我觉得这可以通过函数更有效地完成,特别是因为我想在子集中创建具有不同时间迭代的子集(例如每周、每隔一周、每月)。我在想可能是一个函数,它需要输入每个子集的天数,然后根据整个数据帧的时间量循环生成子集?还是不可能将日期作为输入,而将# of subsets 作为输入会更有意义?

你会如何编写一个可以做到这一点的函数?提前感谢您的帮助!

【问题讨论】:

    标签: r function dataframe subset


    【解决方案1】:

    考虑分配一个月份变量,然后使用split 构建一个数据框列表,该列表比单独的类似月份数据框提供更好的管理。

    mydata$date <- as.POSIXct(mydata$date, format="%m/%d/%y %H:%M") 
    mydata$month <- format(mydata$date,"%m")
    
    month_df_list <- split(mydata, mydata$month)
    
    # OCTOBER DATA FRAME
    month_df_list$`10`
    
    # NOVEMBER DATA FRAME
    month_df_list$`11`
    
    # DECEMBER DATA FRAME
    month_df_list$`12`
    

    请注意,如果存储在列表中,您不会丢失数据框的功能。并重命名:

    month_df_list <- setNames(mydata, paste0("t", seq_along(month_df_list)))
    
    # OCTOBER DATA FRAME
    month_df_list$t1
    
    # NOVEMBER DATA FRAME
    month_df_list$t2
    
    # DECEMBER DATA FRAME
    month_df_list$t3
    

    【讨论】:

      【解决方案2】:

      data.table 方法

      library( data.table )
      

      样本数据

      dt <- fread("id date dummy
      1  2018-10-01T21:41:00     A
      2  2018-10-03T21:41:00     B
      3  2018-10-12T21:41:00     C
      4  2018-11-01T21:41:00     D
      5  2018-11-02T21:41:00     E
      6  2018-11-12T21:41:00     F
      7  2018-11-15T21:41:00     G
      8  2018-12-02T21:41:00     H
      9  2018-12-07T21:41:00     I
      10 2018-12-12T21:41:00     J", header = TRUE)
      
      #set dates as Date
      dt[, date := as.Date( date, format = "%Y-%m-%dT%H:%M:%S", tz = "Europe/Amsterdam" )]
      

      子集

      #subset by month == 10
      dt[ month(date) == 10,]
      
      #    id       date dummy
      # 1:  1 2018-10-01     A
      # 2:  2 2018-10-03     B
      # 3:  3 2018-10-12     C
      
      #list with subset for each month
      lapply( unique(month(dt$date)), function(x) dt[ month(date) == x, ])
      
      # [[1]]
      #    id       date dummy
      # 1:  1 2018-10-01     A
      # 2:  2 2018-10-03     B
      # 3:  3 2018-10-12     C
      # 
      # [[2]]
      #    id       date dummy
      # 1:  4 2018-11-01     D
      # 2:  5 2018-11-02     E
      # 3:  6 2018-11-12     F
      # 4:  7 2018-11-15     G
      # 
      # [[3]]
      #    id       date dummy
      # 1:  8 2018-12-02     H
      # 2:  9 2018-12-07     I
      # 3: 10 2018-12-12     J
      

      【讨论】:

      • 这太好了,谢谢!我是 R 新手,还没有听说过 data.table,这是一个很好的解决方法。这里的输入是月份;有没有办法按周输入子集?还是每隔一周?
      • @c.lam 您可以使用data.table-package 中的isoweek,但是在处理时间/日期时,lubridate-package 中的函数也值得一看..
      猜你喜欢
      • 1970-01-01
      • 2022-01-17
      • 1970-01-01
      • 2022-01-04
      • 2022-01-17
      • 1970-01-01
      • 1970-01-01
      • 1970-01-01
      • 2019-05-13
      相关资源
      最近更新 更多