2013-10-26 58 views
2

我有一个关于动态子集数据表的问题。我知道在stackoverflow上有很多类似计价的线程,但不幸的是他们没有把我带到想要的解决方案。动态子集数据表

的示例数据集:

require(data.table) 
dt <- data.table(date=c(rep(1,5),rep(2,5)),id=rep(1:5,2),var=c(1:10)) 

对于每个ID我想的所有期间的所有其他的ID之前找到的的子集。在示例数据集中有5个ID和两个句点。如果在期间2中查看ID = 5,则对应的子集将是ID = {1,2,3,4)并且日期= 1。在这个简单的数据集我当然可以手工编写此:

dt[,dt[-.I][date<2],by=id] 

然而,我想自动执行此操作。我试过类似

dt[,dt[-.I][date < unique(dt$date[.I])],by=id] 

但这不起作用。

任何有用的意见感谢!谢谢!

+6

如果您评价我的问题,请留下评论,以便我可以改进问题。谢谢! – chameau13

+1

噢,对不起:我过去提出了一些你的问题,但是呃,我认为这个问题背后的基本思想(创造大量的冗余数据)在大多数应用中被误导了(例如,计算条件概率就像你之前的q),并且你之前曾问过几次。此外,它是错误的指定,因为你把“每个ID的所有时期之前”,这实际上意味着你想要“每个ID和日期”,如下面的答案所示。相关元:http://meta.stackexchange.com/q/18552/209360 – Frank

+0

或者,也许这一个:http://meta.stackexchange.com/questions/8891/is-dont-do-it-a-valid-答案 – Frank

回答

2

我觉得这是更快的解决方案:

dta <- data.table(date=c(rep(1,5),rep(2,5)),id=rep(1:5,2),var=c(1:10)) 
dta[,dta[dta[.I]$id!=dta$id & dta[.I]$date>dta$date],by=list(id,date)] 

如何使这个代码更快的高度赞赏任何意见。

3

你必须认识到,随着唯一日期/ ID数量的增加,组合爆炸。即使对于date = 1:10和id = 1:10,答案也是4050行(需要0.7秒),对于date = 1:50和id = 1:50,它已经是3001250行(需要6.2秒)。话虽如此,这应该工作打算:

setkey(dt, date, id) 
ans <- dt[!J(1), {d.tmp = date-1; id.tmp = id; dt[CJ(1:d.tmp, 
     setdiff(id, id.tmp))]}, by=list(date, id)] 
setnames(ans, make.unique(names(ans))) 
setkey(ans, date, id, date.1) 

    date id date.1 id.1 var 
1: 2 1  1 2 2 
2: 2 1  1 3 3 
3: 2 1  1 4 4 
4: 2 1  1 5 5 
5: 2 2  1 1 1 
6: 2 2  1 3 3 
7: 2 2  1 4 4 
8: 2 2  1 5 5 
9: 2 3  1 1 1 
10: 2 3  1 2 2 
11: 2 3  1 4 4 
12: 2 3  1 5 5 
13: 2 4  1 1 1 
14: 2 4  1 2 2 
15: 2 4  1 3 3 
16: 2 4  1 5 5 
17: 2 5  1 1 1 
18: 2 5  1 2 2 
19: 2 5  1 3 3 
20: 2 5  1 4 4 
+0

结果是正确的,但执行对我而言太慢了。如果我找到解决方案,我将编辑到您的回复中。非常感谢你! – chameau13