使用多个匹配在data.table中滚动连接

时间:2013-06-20 14:50:00

标签: r data.table rolling-computation

我对滚动连接有一个评论/问题 设X,Y为:

set.seed(123);
X <- data.table(x=c(1,1,1,2,2),y=c(T,T,F,F,F),t=as.POSIXct("08:00:00.000",format="%H:%M:%OS")+sample(0:999,5,TRUE)/1e3)
Y <- copy(X)
set.seed(123)
Y[,`:=`(IDX=.I,t=t+sample(c(-5:5)/1e3,5,T))]
Y <- rbindlist(list(Y, X[5,][,IDX:=6][,t:=t+0.001], X[5,][,IDX:=7][,t:=t+0.002]))
setkey(X,x,y,t)
setkey(Y,x,y,t)

此处XYx,y,t

排序
R) X
   x     y                       t
1: 1 FALSE 2013-06-20 08:00:00.407
2: 1  TRUE 2013-06-20 08:00:00.286
3: 1  TRUE 2013-06-20 08:00:00.788
4: 2 FALSE 2013-06-20 08:00:00.882
5: 2 FALSE 2013-06-20 08:00:00.940
R) Y
   x     y                       t IDX
1: 1 FALSE 2013-06-20 08:00:00.407   3
2: 1  TRUE 2013-06-20 08:00:00.284   1
3: 1  TRUE 2013-06-20 08:00:00.791   2
4: 2 FALSE 2013-06-20 08:00:00.886   4
5: 2 FALSE 2013-06-20 08:00:00.940   6
6: 2 FALSE 2013-06-20 08:00:00.942   7
7: 2 FALSE 2013-06-20 08:00:00.945   5

来自

执行Y[X, roll=-0.005]让你

R) Y[X, roll=-0.005]
       x     y                       t IDX
    1: 1 FALSE 2013-06-20 08:00:00.407  NA => due to precision the roll is no match
    2: 1  TRUE 2013-06-20 08:00:00.286  NA => ok 
    3: 1  TRUE 2013-06-20 08:00:00.788   2 => ok (x,y) matched and 788-791=-3
    4: 2 FALSE 2013-06-20 08:00:00.882   4 => same
    5: 2 FALSE 2013-06-20 08:00:00.940   6 => NOT AN EXACT MATCH (precision)

所以我希望在最后一行获得更多行,因为“mult”的默认行为是“all”,X的最后一行与5,6, may be 7的{​​{1}}匹配1}}

1 个答案:

答案 0 :(得分:3)

第一行

对于X的第一行,只有Y的第一行匹配xy,因此Y的第一行将匹配iff { {1}}介于Y$t[1]X$t[1]之间,但实际上X$t[1] + 0.005如下所示:

Y$t[1] < X$t[1]

需要一个正> X$t[1] - Y$t[1] Time difference of 0.0009999275 secs 值,其大小至少等于上述差值,以便在第1行获得非NA。例如

roll=

请注意,您可以使用> Y[X, roll=0.001] x y t IDX 1: 1 FALSE 2013-06-20 08:00:00 3 2: 1 TRUE 2013-06-20 08:00:00 NA 3: 1 TRUE 2013-06-20 08:00:00 NA 4: 2 FALSE 2013-06-20 08:00:00 NA 5: 2 FALSE 2013-06-20 08:00:00 NA 强制执行此操作:

rollends=

最后一行

对于> Y[X, roll = -0.005, rollends = TRUE] x y t IDX 1: 1 FALSE 2013-06-20 08:00:00 3 2: 1 TRUE 2013-06-20 08:00:00 NA 3: 1 TRUE 2013-06-20 08:00:00 2 4: 2 FALSE 2013-06-20 08:00:00 4 5: 2 FALSE 2013-06-20 08:00:00 6 的最后一行,X匹配的第5行,而不是5,6和7,因为只有最近的符合条件的行匹配。 Y仅适用于多个匹配,通常不适用于mult=(请参阅底部的示例以了解异常):

另请注意,roll=的第5,6和7行的时间不同。他们的时间越来越多,所以他们都不可能匹配:

Y

即使> dput(Y[["t"]]) structure(c(1371729600.407, 1371729600.285, 1371729600.791, 1371729600.887, 1371729600.941, 1371729600.942, 1371729600.945), class = c("POSIXct", "POSIXt")) 的第5,6和7行具有相同的时间,如果这些时间与Y的最后一行中的时间不同,那么只有一行只能获得一行。

X

只有当'Y'的第5,6和7行具有相同的时间时,> # times in rows 5, 6 and 7 of Y2 are same > Y2 <- copy(Y) > Y2[, t:= t[c(1:4, 5, 5, 5)]] > setkey(Y2, x, y, t) > Y2[X, roll = -0.005] x y t IDX 1: 1 FALSE 2013-06-20 08:00:00 NA 2: 1 TRUE 2013-06-20 08:00:00 NA 3: 1 TRUE 2013-06-20 08:00:00 2 4: 2 FALSE 2013-06-20 08:00:00 4 5: 2 FALSE 2013-06-20 08:00:00 6 的最后一行才会有一次多次出现并且在那里案例X可以适用:

mult=

文档中的工作原理并不是很清楚,我不得不使用反复试验来发现它的功能。 > # time in row 5 of X2 same as the times in rows 5, 6 and 7 of Y2 > X2 <- copy(X) > X2[, t:=c(t[1:4], Y2[["t"]][5])] > Y2[X2, roll = -0.005] x y t IDX 1: 1 FALSE 2013-06-20 08:00:00 NA 2: 1 TRUE 2013-06-20 08:00:00 NA 3: 1 TRUE 2013-06-20 08:00:00 2 4: 2 FALSE 2013-06-20 08:00:00 4 5: 2 FALSE 2013-06-20 08:00:00 6 6: 2 FALSE 2013-06-20 08:00:00 7 7: 2 FALSE 2013-06-20 08:00:00 5 > > Y2[X, roll = -0.005, mult = "first"] x y t IDX 1: 1 FALSE 2013-06-20 08:00:00 NA 2: 1 TRUE 2013-06-20 08:00:00 NA 3: 1 TRUE 2013-06-20 08:00:00 2 4: 2 FALSE 2013-06-20 08:00:00 4 5: 2 FALSE 2013-06-20 08:00:00 6 确实说“通常,x的密钥中应该没有重复”(在我们的示例中,这里x是?data.table)所以可能是开发人员希望离开它对于这种情况是不确定的,并且对未来的变化持开放态度。

在您描述时使用Y的想法看起来确实是一个非常有趣的想法,但似乎不是它目前的工作方式。也许它可以在未来。