在组内分离非重叠间隔并在R中计数
使用R,我得到了住院患者数据,我根据(病原体的)DNA菌株、住院患者的临床和重叠的住院时间进行分组,以确定是否可能传播 我需要对重叠的组进行顺序编号。这看起来很简单,但有两个问题:在组内分离非重叠间隔并在R中计数,r,date,R,Date,使用R,我得到了住院患者数据,我根据(病原体的)DNA菌株、住院患者的临床和重叠的住院时间进行分组,以确定是否可能传播 我需要对重叠的组进行顺序编号。这看起来很简单,但有两个问题: 我在SO或其他网站上找到的所有内容都是关于对组中的行进行编号的。我需要一组中的每一行都有相同的数字,并且需要对组本身进行计数 无论采用何种方法,最初看起来都很简单,只需(应变、临床)%%>%,但这并不能解释不重叠的时间间隔 在最终让步并发布到这里之前,我尝试了几种方法并进行了搜索(我的任何尝试都不值得在这里发布事件以
拥有的
)和我想要的数据(想要的
)的一个示例。注:对于应变B
,所有患者都在诊所1
,但由于时间间隔不同,分为两组
任何建议都将不胜感激
have <- data.frame(id=c("K01","K02","K03","K04","K05","K06","K07","K08","K09"),
strain=c(rep("A",4),rep("B",5)),
clinic=c(rep("Clinic_1",2),rep("Clinic_2",2),rep("Clinic_1",5)),
datein=as.Date(c("2020/01/01","2020/01/03","2020/02/03","2020/02/09","2020/02/18","2020/02/20","2020/02/21","2020/03/06","2020/03/18")),
dateout=as.Date(c("2020/01/05","2020/01/16","2020/02/09","2020/02/19","2020/02/27","2020/02/23","2020/02/22","2020/03/21","2020/03/22"))
)
want <- data.frame(have,overlap_number=c(1,1,2,2,3,3,3,4,4))
#How the final data would look
> View(want)
id strain clinic datein dateout overlap_number
1 K01 A Clinic_1 2020-01-01 2020-01-05 1
2 K02 A Clinic_1 2020-01-03 2020-01-16 1
3 K03 A Clinic_2 2020-02-03 2020-02-09 2
4 K04 A Clinic_2 2020-02-09 2020-02-19 2
5 K05 B Clinic_1 2020-02-18 2020-02-27 3
6 K06 B Clinic_1 2020-02-20 2020-02-23 3
7 K07 B Clinic_1 2020-02-21 2020-02-22 3
8 K08 B Clinic_1 2020-03-06 2020-03-21 4
9 K09 B Clinic_1 2020-03-18 2020-03-22 4
我们可以使用
rleid
library(dplyr)
library(data.table)
have %>%
mutate(overlap_number = rleid(strain, clinic,
cumsum(datein > lag(dateout, default = first(dateout)))))
# id strain clinic datein dateout overlap_number
#1 K01 A Clinic_1 2020-01-01 2020-01-05 1
#2 K02 A Clinic_1 2020-01-03 2020-01-16 1
#3 K03 A Clinic_2 2020-02-03 2020-02-09 2
#4 K04 A Clinic_2 2020-02-09 2020-02-19 2
#5 K05 B Clinic_1 2020-02-18 2020-02-27 3
#6 K06 B Clinic_1 2020-02-20 2020-02-23 3
#7 K07 B Clinic_1 2020-02-21 2020-02-22 3
#8 K08 B Clinic_1 2020-03-06 2020-03-21 4
#9 K09 B Clinic_1 2020-03-18 2020-03-22 4
使用
数据的选项。表
:
setkey(setDT(have), clinic, strain, datein, dateout)
have[, g := cumsum(c(0L, (shift(datein, -1L) > cummax(as.integer(dateout)))[-.N])),
.(clinic, strain)][,
g := rleid(clinic, strain, g)]
此外:
输出:
id strain clinic datein dateout g g2
1: K01 A Clinic_1 2020-01-01 2020-01-05 1 1
2: K02 A Clinic_1 2020-01-03 2020-01-16 1 1
3: K05 B Clinic_1 2020-02-18 2020-02-27 2 2
4: K06 B Clinic_1 2020-02-20 2020-02-23 2 2
5: K07 B Clinic_1 2020-02-21 2020-02-22 2 2
6: K08 B Clinic_1 2020-03-06 2020-03-21 3 3
7: K09 B Clinic_1 2020-03-18 2020-03-22 3 3
8: K03 A Clinic_2 2020-02-03 2020-02-09 4 4
9: K04 A Clinic_2 2020-02-09 2020-02-19 4 4
关于
cummax
的想法来自David Aurenburg post:Beauty-不知道rleid函数,并且在示例数据上工作得非常完美。当我把它应用到我的实际数据中时,会有一个小小的小问题——3+的数据组有时会有一个很长的间隔,包括其他几个不连贯的日期。例如,我编辑了另一个数据集,该数据集更改了K07的日期。我尝试将延迟(dateout…更改为分钟(dateout…),但没有成功。还有其他想法吗?@jpsmith是您需要的相同重叠编号我添加了我的输出和注释;当我在want2上运行它时,它会创建5个重叠数字,因为它将K07
视为一个单独的单元感谢您的深入了解-在这个解决方案中,K07与K08和K09分组,但应与K05/K06分组。根据你的方法,我尝试了几种选择,但都没能奏效。有什么想法吗?谢谢你迄今为止的帮助!完美的非常感谢。
have[, g02 := cumsum(datein > shift(cummax(as.integer(dateout)), fill=dateout[1L])),
.(clinic, strain)][,
g2 := rleid(clinic, strain, g02)]
id strain clinic datein dateout g g2
1: K01 A Clinic_1 2020-01-01 2020-01-05 1 1
2: K02 A Clinic_1 2020-01-03 2020-01-16 1 1
3: K05 B Clinic_1 2020-02-18 2020-02-27 2 2
4: K06 B Clinic_1 2020-02-20 2020-02-23 2 2
5: K07 B Clinic_1 2020-02-21 2020-02-22 2 2
6: K08 B Clinic_1 2020-03-06 2020-03-21 3 3
7: K09 B Clinic_1 2020-03-18 2020-03-22 3 3
8: K03 A Clinic_2 2020-02-03 2020-02-09 4 4
9: K04 A Clinic_2 2020-02-09 2020-02-19 4 4