【发布时间】:2016-07-19 23:33:37
【问题描述】:
我正在尝试计算行数,直到在分组数据框中达到某个条件。我试图调整解决方案 here 但这似乎不适用于团体。
样本数据:
grp <- c(rep(1:2, each = 5), 3)
fromdate <- as.Date(c("2010-06-01", "2012-02-01", "2013-02-01", "2013-02-01", "2015-10-01", "2011-02-01", "2011-03-01", "2013-04-01", "2013-06-01", "2013-10-01", "2012-02-01"), origin = "1970-01-01")
todate <- as.Date(c("2016-12-31", "2013-01-31", "2015-10-31", "2015-12-31", "2016-01-31", "2013-02-28", "2013-02-28", "2013-09-30", "2016-12-31", "2017-01-31", "2014-01-31"), origin = "1970-01-01")
df <- data.frame(grp, fromdate, todate)
我的最终目标是每个组的每个连续覆盖期都有一条线路。为此,我需要执行以下操作: 1) 识别日期完全在前一行的日期内的行(即 fromdate 较大,todate 较小)。然后我会删除这些日期飞地。 2)识别当前行的fromdate何时小于前一行的todate,即存在重叠覆盖。然后,我会将第一行的 todate 重写为该连续覆盖期间的最新 todate,并删除其他行。
我有代码要做 2),但我在第 1 部分中苦苦挣扎。
到目前为止,我的方法是按 fromdate 排序并向下搜索 todate,直到找到更大的 todate。这将是所需的输出:
grp fromdate todate drop
1 2010-06-01 2016-12-31 0
1 2012-02-01 2013-01-31 1
1 2013-02-01 2015-10-31 1
1 2013-02-01 2015-12-31 1
1 2015-10-01 2016-01-31 1
2 2011-02-01 2013-02-28 0
2 2011-03-01 2013-02-28 1
2 2013-04-01 2013-09-30 0
2 2013-06-01 2016-12-31 0
2 2013-10-01 2017-01-31 0
3 2012-02-01 2014-01-31 0
应用第 2 部分)后,最终的 df 应该是这样的:
grp fromdate todate
1 2010-06-01 2016-12-31
2 2011-02-01 2013-02-28
2 2013-04-01 2017-01-31
3 2012-02-01 2014-01-31
这可以计算到较大日期之前的行数,但仅限于未分组的数据:
df <- df %>%
arrange(grp, fromdate, todate) %>%
mutate(rows_to_max = sapply(1:length(todate),
function(x) min(which(.$todate[x:length(.$todate)] > .$todate[x]))-1)) %>%
ungroup()
我希望该解决方案与 dplyr 保持兼容,但对其他选项持开放态度。
提前致谢。
【问题讨论】:
-
“前一行”是指任何行,还是仅指前一行?
-
该组中的任何前一行。
-
第一个框中的代码已停止工作
-
你的答案看起来也很清晰,也许把它作为答案?
-
我修复了虚拟数据代码,它应该可以创建第三组