如何获得 R 中日期间隔的重叠值
How to obtain overlapping values for intervals of dates in R
我有一个如下所示的数据框:
w<-read.table(header=TRUE, text="
start.date end.date manager
2006-05-01 2007-04-30 a
2006-09-30 2007-12-31 b
1999-09-30 2007-12-31 c
2008-01-01 2012-04-30 d
2008-01-01 2020-02-28 e
2009-05-01 2016-04-08 f")
我想获得一个数据框,其中 returns 哪些经理在此期间的每个月都在工作,例如
df<-read.table(header=TRUE, text="
month manager1 manager2 manager3 manager4
01-2006 a b c NA
02-2006 a b c d
03-2006 b c d NA
04-2006 b d NA NA")
我首先定义了一个函数 datseq returns start.date 和 end.date
datseq <- function(t1, t2) {
format(seq.Date(from = as.Date(t1,"%Y-%m-%d"),
to = as.Date(t2,"%Y-%m-%d"),by="month"),
"%m/%Y")
但后来我无法创建适当的循环来获得所需的结果。
提前谢谢大家的回复!
由于您只需要知道月级别的重叠而不是天级别,您可以认为经理在第 1 天开始工作并在每月的最后一天离开。这可以使用包 lubridate
.
中的 floor_date
和 ceiling_date
来实现
library(lubridate)
w.extended <- w
w.extended$start.date <- floor_date(as.Date(w.extended$start.date), "month")
w.extended$end.date <- ceiling_date(as.Date(w.extended$end.date), "month") - 1
#List of months
timeperiod <- seq(min(w.extended$start.date),
by = "month",
to = max(w.extended$end.date))
然后您可以使用包 lubridate
中的 a %within% b
,它可以检查日期是否在间隔列表中。按照您提供的时间间隔将此函数应用于您的每个月。
df <- data.frame(t(sapply(timeperiod,
function(x){
managersWorking <- x %within% interval(w.extended$start.date,
w.extended$end.date)
c(as.character(x), managersWorking)
})),
stringsAsFactors = F)
#Replace the 'character' format of columns to the appropriate one
df[-1] <- apply(df[-1], 2, as.logical)
df[,1]<- format(as.Date(df[,1]), "%Y/%m")
colnames(df) <- c("month", paste0("manager.", w$manager))
head(df)
# month manager.a manager.b manager.c manager.d manager.e manager.f
#1 1999/09 FALSE FALSE TRUE FALSE FALSE FALSE
#2 1999/10 FALSE FALSE TRUE FALSE FALSE FALSE
#3 1999/11 FALSE FALSE TRUE FALSE FALSE FALSE
#4 1999/12 FALSE FALSE TRUE FALSE FALSE FALSE
#5 2000/01 FALSE FALSE TRUE FALSE FALSE FALSE
#6 2000/02 FALSE FALSE TRUE FALSE FALSE FALSE
原始数据:
w <- read.table(header=TRUE, text="
start.date end.date manager
2006-05-01 2007-04-30 a
2006-09-30 2007-12-31 b
1999-09-30 2007-12-31 c
2008-01-01 2012-04-30 d
2008-01-01 2020-02-28 e
2009-05-01 2016-04-08 f")
w
# start.date end.date manager
#1 2006-05-01 2007-04-30 a
#2 2006-09-30 2007-12-31 b
#3 1999-09-30 2007-12-31 c
#4 2008-01-01 2012-04-30 d
#5 2008-01-01 2020-02-28 e
#6 2009-05-01 2016-04-08 f
我有一个如下所示的数据框:
w<-read.table(header=TRUE, text="
start.date end.date manager
2006-05-01 2007-04-30 a
2006-09-30 2007-12-31 b
1999-09-30 2007-12-31 c
2008-01-01 2012-04-30 d
2008-01-01 2020-02-28 e
2009-05-01 2016-04-08 f")
我想获得一个数据框,其中 returns 哪些经理在此期间的每个月都在工作,例如
df<-read.table(header=TRUE, text="
month manager1 manager2 manager3 manager4
01-2006 a b c NA
02-2006 a b c d
03-2006 b c d NA
04-2006 b d NA NA")
我首先定义了一个函数 datseq returns start.date 和 end.date
datseq <- function(t1, t2) {
format(seq.Date(from = as.Date(t1,"%Y-%m-%d"),
to = as.Date(t2,"%Y-%m-%d"),by="month"),
"%m/%Y")
但后来我无法创建适当的循环来获得所需的结果。 提前谢谢大家的回复!
由于您只需要知道月级别的重叠而不是天级别,您可以认为经理在第 1 天开始工作并在每月的最后一天离开。这可以使用包 lubridate
.
floor_date
和 ceiling_date
来实现
library(lubridate)
w.extended <- w
w.extended$start.date <- floor_date(as.Date(w.extended$start.date), "month")
w.extended$end.date <- ceiling_date(as.Date(w.extended$end.date), "month") - 1
#List of months
timeperiod <- seq(min(w.extended$start.date),
by = "month",
to = max(w.extended$end.date))
然后您可以使用包 lubridate
中的 a %within% b
,它可以检查日期是否在间隔列表中。按照您提供的时间间隔将此函数应用于您的每个月。
df <- data.frame(t(sapply(timeperiod,
function(x){
managersWorking <- x %within% interval(w.extended$start.date,
w.extended$end.date)
c(as.character(x), managersWorking)
})),
stringsAsFactors = F)
#Replace the 'character' format of columns to the appropriate one
df[-1] <- apply(df[-1], 2, as.logical)
df[,1]<- format(as.Date(df[,1]), "%Y/%m")
colnames(df) <- c("month", paste0("manager.", w$manager))
head(df)
# month manager.a manager.b manager.c manager.d manager.e manager.f
#1 1999/09 FALSE FALSE TRUE FALSE FALSE FALSE
#2 1999/10 FALSE FALSE TRUE FALSE FALSE FALSE
#3 1999/11 FALSE FALSE TRUE FALSE FALSE FALSE
#4 1999/12 FALSE FALSE TRUE FALSE FALSE FALSE
#5 2000/01 FALSE FALSE TRUE FALSE FALSE FALSE
#6 2000/02 FALSE FALSE TRUE FALSE FALSE FALSE
原始数据:
w <- read.table(header=TRUE, text="
start.date end.date manager
2006-05-01 2007-04-30 a
2006-09-30 2007-12-31 b
1999-09-30 2007-12-31 c
2008-01-01 2012-04-30 d
2008-01-01 2020-02-28 e
2009-05-01 2016-04-08 f")
w
# start.date end.date manager
#1 2006-05-01 2007-04-30 a
#2 2006-09-30 2007-12-31 b
#3 1999-09-30 2007-12-31 c
#4 2008-01-01 2012-04-30 d
#5 2008-01-01 2020-02-28 e
#6 2009-05-01 2016-04-08 f