【发布时间】:2019-05-06 17:04:25
【问题描述】:
请注意,我已经使用 dplyr 编写了一些代码来满足我的需求,但感觉非常笨拙,我想知道是否有更优雅的解决方案
我有一个简化的数据框,本质上是这样的:
df = data.frame(
id = c(1,1,1,2,2,2),
date = as.Date(c('2018/01/01', '2018/01/02',
'2018/01/03', '2018/01/01', '2018/01/02', '2018/06/01'))
)
id date
1 1 2018-01-01
2 1 2018-01-02
3 1 2018-01-03
4 2 2018-01-01
5 2 2018-01-02
6 2 2018-06-01
我想要一个表格,显示每个 id 的第一条记录后 30 天内的记录数和最后一条记录后 30 天内的记录数。对于这个简单的版本,输出应该是这样的:
id start.records end.records
1 3 3
2 2 1
我可以用这段代码得到我想要的输出:
df %>%
group_by(id) %>%
summarize(min.date = min(date)) %>%
mutate(min.date.plus.30 = min.date + 30) %>%
fuzzy_left_join(
df,
by = list(x=c("id", "min.date.plus.30"), y=c("id", "date")),
match_fun = list(`==`, `>`)
) %>%
group_by(id.x, min.date) %>%
summarize(start.records = n()) %>%
left_join(
df %>%
group_by(id) %>%
summarize(max.date = max(date)) %>%
mutate(max.date.minus.30 = max.date - 30) %>%
fuzzy_left_join(
df,
by = list(x=c("id", "max.date.minus.30"), y=c("id", "date")),
match_fun = list(`==`, `<`)
) %>%
group_by(id.x, max.date) %>%
summarize(end.records = n()),
by = "id.x"
)
但这似乎是一个非常不雅的解决方案。
有没有更好的方法来做到这一点?我宁愿不使用 sqldf,因为它不能轻松处理日期计算,而且我的真实数据集有 150,000 多行,即使是简单的 sqldf 测试查询也需要永远运行。
提前感谢您的帮助!
【问题讨论】:
-
除 sqlite 之外的任何 sqldf 后端都可以轻松处理日期。试试 H2。