2016-06-30 48 views
1

我有ID的數據幀(df1),日期被按升序以(1)ID &(2)日期排序:基於組級子集R數據幀值

ID____Date 
1_____1990-01-01 
1_____1991-01-01 
1_____1992-01-01 
1_____1993-01-01 
2_____1990-01-01 
2_____1991-01-01 
3_____1990-01-01 
3_____1991-01-01 
3_____1992-01-01 

我想到子集基於從以下數據幀組的電平值(df2)上面的數據幀:

ID____Date 
1_____1993-01-01 
2_____1990-01-01 
3_____1991-01-01 

子集條件:選擇在df1針對日期小於或等於特定的ID的所有行(<=df2中對應ID的日期。

在上述例子中所期望的輸出是:

ID____Date 
1_____1991-01-01 
1_____1992-01-01 
1_____1993-01-01 
2_____1990-01-01 
3_____1990-01-01 
3_____1991-01-01 

回答

1

我們可以使用data.table。將'data.frame'轉換爲'data.table'(setDT(df1)),與'df2'on'ID'列結合,將'Date'小於或等於'i.Date'的行子集,並賦值(:=)'i.Date'爲NULL。

library(data.table) 
setDT(df1)[df2, on = 'ID'][Date <= i.Date][, i.Date := NULL] 

或者,這可以在一個單一的步驟

setDT(df1)[df2, .SD[Date <= i.Date], on = 'ID', by = .EACHI] 
# ID  Date 
#1: 1 1990-01-01 
#2: 1 1991-01-01 
#3: 1 1992-01-01 
#4: 1 1993-01-01 
#5: 2 1990-01-01 
#6: 3 1990-01-01 
#7: 3 1991-01-01 

或者

setDT(df1)[df2, .SD[Date <= i.Date] ,on = 'ID'] 

我們也可以做到這一點使用base R

完成
df1[df1$Date <= df2$Date[match(df1$ID, df2$ID)],] 
# ID  Date 
#1 1 1990-01-01 
#2 1 1991-01-01 
#3 1 1992-01-01 
#4 1 1993-01-01 
#5 2 1990-01-01 
#7 3 1990-01-01 
#8 3 1991-01-01 
+0

基礎R解決方案的工作比data.table和sqldf快得多。在1秒內處理了200萬行,而對於sqldf爲20秒,數據爲2秒。表 –

+1

@NaveenMathew這是因爲不是加入,我們使用'match'來獲取索引。它快得多。 – akrun

1

它可與sqldf也可以做:

library(sqldf) 
sqldf("select a.* from df1 a, df2 b where a.Date <= b.Date AND a.ID = b.ID")