2017-10-09 111 views
3

我已經使用dplyr代碼慢速data.table子集VS dplyr

group_by(dt, ID) %>% 
    filter(any(colY == 1 & colX == 10)) 

以下格式到子集像下面

 
ID colX colY 
1111 3 1 
1111 2 1 
1111 6 0 
1111 9 0 
2222 10 1 
2222 3 1 
2222 5 0 
2222 7 0 
3333 8 1 
3333 10 1 
3333 3 0 
3333 2 0 

一個data.table成

 
ID colX colY 
2222 10 1 
2222 3 1 
2222 5 0 
2222 7 0 
3333 8 1 
3333 10 1 
3333 3 0 
3333 2 0 

通過約900k行過濾得到第二張表需要大約1.3秒。

我一直在試圖實現一個data.table子集,它會更快,但到目前爲止結果只需要更長的時間。使用以下data.table子集

dt[ , .SD[any((colY == 1 & colX == 10)) ], ID] 

需要大約14秒。這裏似乎是什麼問題?

+0

,10]是你的'ID'列的位置?也許你會生成一些模擬數據,這樣很容易爲你找出現實的解決方案。 – russellpierce

+1

我很抱歉應該按照ID – Alex

回答

4

這可能會更快。它避免使用.SD,並使用.I中給出的行號代替。

dt[dt[, .I[any(colX == 10 & colY == 1)], by = ID]$V1] 
#  ID colX colY 
# 1: 2222 10 1 
# 2: 2222 3 1 
# 3: 2222 5 0 
# 4: 2222 7 0 
# 5: 3333 8 1 
# 6: 3333 10 1 
# 7: 3333 3 0 
# 8: 3333 2 0 

內部數據表調用dt[, .I[any(colX == 10 & colY == 1)], by = ID]$V1給了我們行號對於那些符合我們的條件組。 .I給我們每組的行位置。我們可以看到,其結果將是通過打印我們的電話是什麼:

dt[, print(.I[any(colX == 10 & colY == 1)]), by = ID] 
# integer(0) 
# [1] 5 6 7 8 
# [1] 9 10 11 12 
# Empty data.table (0 rows) of 1 col: ID 

然後,我們只需要使用結果作爲原始數據表中的行子集。

+3

分組,結果比我嘗試的data.table子集快了75倍。 .SD正在拉動90k組,這會減慢過程很多 – Alex

+1

聯接是另一種方式,如果有很多組DT'(DT [。(1,10),on = c(「 colY「,」colX「),unique(ID)]),on =」ID「]'將此添加到'having ='參數的鏈接堆中https://github.com/Rdatatable/data.table /問題/ 788 – Frank