【问题标题】:Specific Matching two dates in two data frames具体匹配两个数据框中的两个日期
【发布时间】:2018-07-14 00:25:53
【问题描述】:

我想得到特定日期之间计数(行)的 sum()。我在堆栈上找到了一些解决方案,但关键是我的第二个数据帧比第一个数据帧大得多。

数据集一

dim(foo1) # 600 / 2

Start                      End
2017-10-24 22:33:59   2017-10-24 22:43:59
2017-11-13 06:34:59   2017-11-13 06:44:59
2017-11-13 06:52:00   2017-11-13 07:02:00
2017-11-13 07:16:59   2017-11-13 07:26:59
2017-11-13 07:35:59   2017-11-13 07:45:59

数据集二

dim(foo2) # 60.000 / 2

Count           Time
1              2017-10-01 13:45:02
1              2017-10-01 12:53:23
1              2017-10-01 12:20:56
1              2017-10-01 12:31:12

我想要 foo2 中出现在 foo1 中的开始日期和结束日期之间的所有行(计数)的总和)。结果应该是 Foo1 + new_column(包含计数)

这是我开始的不起作用的“解决方案”:

for(i in 1:nrow(foo1)){
  foo1$new_column[i] <-sum(foo2$Count[which( 
    foo2$Time >= foo2$Start[i] &
      foo2$Time <= foo2$End[i])]) 
}

【问题讨论】:

  • 您问的问题和one here 完全相同吗?你甚至有相同的时间框架和不重叠。
  • 样本数据似乎不正确。来自foo2$Time 的时间戳没有落在foo1$Start - foo1$End 的范围内
  • 我猜我们是同一个类的phiver。抱歉没找到。

标签: r join time


【解决方案1】:

您的示例数据中似乎存在问题,因为来自foo2Time(均在 2017 年 10 月 1 日)不在foo1 的时间间隔内(范围从 2017 年 10 月开始-24) .

对于这个答案,我创建了自己的示例数据。

library(data.table)

foo1 <- data.table( Start = c("2017-10-24 22:33:59", "2017-11-13 06:34:59", "2017-11-13 06:52:00", "2017-11-13 07:16:59", "2017-11-13 07:35:59"),
                    End = c("2017-10-24 22:43:59", "2017-11-13 06:44:59", "2017-11-13 07:02:00", "2017-11-13 07:26:59", "2017-11-13 07:45:59"),
                    stringsAsFactors = FALSE)

#                  Start                 End
# 1: 2017-10-24 22:33:59 2017-10-24 22:43:59
# 2: 2017-11-13 06:34:59 2017-11-13 06:44:59
# 3: 2017-11-13 06:52:00 2017-11-13 07:02:00
# 4: 2017-11-13 07:16:59 2017-11-13 07:26:59
# 5: 2017-11-13 07:35:59 2017-11-13 07:45:59

foo2 <- data.table( Count = c(1,1,1,1),
                    Time = c("2017-10-24 22:37:02", "2017-10-24 22:38:23", "2017-11-13 07:20:56", "2017-10-01 12:31:12"),
                    stringsAsFactors = FALSE)

#    Count                Time
# 1:     1 2017-10-24 22:37:02
# 2:     1 2017-10-24 22:38:23
# 3:     1 2017-11-13 07:20:56
# 4:     1 2017-10-01 12:31:12

#set times as POSIXct
foo1[, Start := as.POSIXct(Start, format = "%Y-%m-%d %H:%M:%S")]
foo1[, End := as.POSIXct(End, format = "%Y-%m-%d %H:%M:%S")]
foo2[, Time :=  as.POSIXct(Time, format = "%Y-%m-%d %H:%M:%S")]

#add a dummy-column to create a time-range (of 1 second)
foo2[, dummy := Time]

#set data.table keys
setkey(foo1, Start, End)
setkey(foo2, Time, dummy)

#overlap-join, lose the dummy-column
foo3 <- foverlaps(foo2, foo1, type = "within", mult = "first", nomatch = 0L)[, dummy := NULL]

#                  Start                 End Count                Time
# 1: 2017-10-24 22:33:59 2017-10-24 22:43:59     1 2017-10-24 22:37:02
# 2: 2017-10-24 22:33:59 2017-10-24 22:43:59     1 2017-10-24 22:38:23
# 3: 2017-11-13 07:16:59 2017-11-13 07:26:59     1 2017-11-13 07:20:56

foo3[, sum(Count), by = "Start"]
#                  Start V1
# 1: 2017-10-24 22:33:59  2
# 2: 2017-11-13 07:16:59  1

【讨论】:

  • 谢谢,但是这个解决方案不会在我的第一个数据框中添加一个列,对吗?结果是一个数据框(包含列:开始、结束、计数(到处都是 1)、时间和虚拟)...
  • @Loesje 计数仍然存在,您可以对任何您喜欢的操作求和...只需使用summarise 或 data.tables by= 来求和计数...
  • 即使在 group_by(Start) 和 summarise(Count) 之后,不幸的是计数不匹配...其中一些匹配,但其他一些则停留在计数,例如 1...
  • 用一些实际有意义的数据更新答案
【解决方案2】:

由于您的原始数据集似乎没有任何重叠,因此我在示例中添加了一个额外的行。我使用dplyr mutate 添加一列,其中包含每个StartEnd 的逐行比较Endfoo2$Time 的整个列表,然后我只是对结果集的foo2$Count 求和。

library(dplyr)
foo2 <- foo2 %>% add_row(Count = 3, Time = as.Date("2017-10-24 22:35:00", tz = "UTC"))
foo1 %>% rowwise() %>%  mutate(Count = sum(foo2$Count[between(as.Date(foo2$Time), as.Date(Start), as.Date(End))]))

#     Source: local data frame [500 x 3]
# Groups: <by row>
# 
# A tibble: 500 x 3
#    Start               End                 Count
#    <dttm>              <dttm>              <dbl>
#  1 2017-10-24 22:33:59 2017-10-24 22:43:59  3.00
#  2 2017-11-13 06:34:59 2017-11-13 06:44:59  0   
#  3 2017-11-13 06:52:00 2017-11-13 07:02:00  0   
#  4 2017-11-13 07:16:59 2017-11-13 07:26:59  0   
#  5 2017-11-13 07:35:59 2017-11-13 07:45:59  0   
#  6 2017-11-13 09:46:00 2017-11-13 09:56:00  0   
#  7 2017-11-13 10:46:00 2017-11-13 10:56:00  0   
#  8 2017-11-13 11:11:00 2017-11-13 11:21:00  0   
#  9 2017-11-13 13:33:00 2017-11-13 13:43:00  0   
# 10 2017-11-13 13:50:59 2017-11-13 14:00:59  0   
# # ... with 490 more rows

【讨论】:

  • 计数不正确。会不会是这样,因为我的 foo1$start、foo1$end 和 foo2$time 是 POSIXct.(格式:“2017-10-01 12:52:25”)。当您在声明中将值设为 as.date 时?
  • 不确定。您有任何数据来支持您的主张吗?
  • 是的,我怎样才能将数据传输给您?由于 dput() 并没有真正工作
  • 对不起,我对stackoverflow没有那么丰富
猜你喜欢
  • 1970-01-01
  • 1970-01-01
  • 1970-01-01
  • 2023-04-10
  • 2020-02-24
  • 1970-01-01
  • 1970-01-01
  • 2021-12-29
  • 1970-01-01
相关资源
最近更新 更多