据说这个问题已经得到解答。但是标记我的问题的用户未能测试解决方案,并且引用的问题对我的问题不起作用。
我发现了有关如何使用其他列表过滤数据框的问题,但我没有找到显示如何使用其他数据框过滤数据框的内容。
我有两个数据帧,第一个可以被认为是ID和日期的关键。
id date
1 id1 2016-06-23
2 id2 2016-06-25
3 id3 2016-06-23
4 id4 2016-06-25
5 id5 2016-06-27
structure(list(id = structure(1:5, .Label = c("id1", "id2", "id3",
"id4", "id5"), class = "factor"), date = structure(c(16975, 16977,
16975, 16977, 16979), class = "Date")), .Names = c("id", "date"
), row.names = c(NA, -5L), class = "data.frame")
然后我有第二个带有ID和日期的数据框,我想过滤第二个数据帧,只返回在第一行中ID的日期之后的行。
这是第二个数据帧:
id date
1 id1 2016-06-20
2 id1 2016-06-23
3 id1 2016-06-24
4 id2 2016-06-23
5 id3 2016-06-27
structure(list(id = structure(c(1L, 1L, 1L, 2L, 3L), .Label = c("id1",
"id2", "id3"), class = "factor"), date = structure(c(16972, 16975,
16976, 16975, 16979), class = "Date")), .Names = c("id", "date"
), row.names = c(NA, -5L), class = "data.frame")
这就是结果的样子:
id date
1 id1 2016-06-24
2 id3 2016-06-27
答案 0 :(得分:3)
data.table
library(data.table)
setDT(df1)
setDT(df2)
setnames(df1, 'date','date1') # disambiguate for conditional join
df1[df2, on=.(id, date1<date), nomatch=0]
返回:
id date1
1: id1 2016-06-24
2: id3 2016-06-27
在大型数据集上,我希望这种方法比使用dplyr
和/或笛卡尔连接后跟过滤器的方法更快。
答案 1 :(得分:1)
感谢上帝有dplyr
。以下代码连接具有唯一标识符的df1
,并仅保留与条件filter
匹配的这些行(date >= date.1
)。
要小心,因为默认情况下,当两个data.frame中都有相同的列名时,dplyr将全部加入。然后我们必须指定by
参数并将后缀添加到变量名称以使不同的列名称不同。
library(dplyr)
library(magrittr)
df2 %>%
left_join(df1, by = "id", suffix=c("",".2") ) %>%
filter( date > date.2) %>%
select( -date.2 )
# id date
# 1 id1 2016-06-23
# 2 id1 2016-06-24
# 3 id3 2016-06-27
答案 2 :(得分:1)
使用data.table
的解决方案:
library(data.table)
setDT(d1)
setDT(d2)
merge(d1, d2, "id")[date.y > date.x, .(id, date = date.y)]
id date
1: id1 2016-06-24
2: id3 2016-06-27
答案 3 :(得分:0)
所以你的第一个数据帧基本上就是一个索引。假设索引被称为df1,而你想要过滤的第二个数据帧是df2,我会用dplyr来做这个:
library(dplyr)
df.result <- left_join(df2, df1, by = "id") %>%
filter(date.x > date.y) %>%
select(-date.y)
eta:结果就是这样:
id date.x
1 id1 2016-06-24
2 id3 2016-06-27