R中的窗口函数?

时间:2012-10-30 12:26:06

标签: r

我试图在R中做一些等同于SQL中“第一个值”窗口函数的东西,例如:

select *, first_value(value3) over (partition by value1, value2 order by value5 desc)
from df

有没有一种很好的方法在R中执行此操作而无需创建数据库来使用sqldf / RPostgreSQL之类的东西?

我在这里看到了其他一些例子:Cumulative sum by group in sqldf?

但是我在使用窗口中的顺序很重要的功能找出如何使用它时遇到了一些麻烦。另一件事是我正在使用~500K行,因此性能是一个问题。

编辑:这是一个例子:

item_id  rental_date   customer_id
I001     10/20/2012    1
I002     10/05/2012    4 
I001     10/15/2012    3
I004     10/19/2012    1
I001     10/11/2012    6
I002     9/15/2012     5
I004     10/13/2012    10
I001     9/30/2012     4

我如何确定每个月租用特定物品的第一位顾客?

2 个答案:

答案 0 :(得分:4)

如果不使用sqldf / PostgreSQL你的意思是使用sqldf但是使用SQLite而不是PostgreSQL然后尝试这个(它依赖于去年添加的SQLite的新功能,如果有最小值或最大值,那么其他列保证来自同一行):

Lines <- "item_id  rental_date   customer_id
I001     10/20/2012    1
I002     10/05/2012    4 
I001     10/15/2012    3
I004     10/19/2012    1
I001     10/11/2012    6
I002     9/15/2012     5
I004     10/13/2012    10
I001     9/30/2012     4"

DF <- read.table(text = Lines, as.is = TRUE, header = TRUE)
DF$rental_date <- as.Date(DF$rental_date, "%m/%d/%Y")
DF$ym <- format(DF$rental_date, "%Y-%m")

sqldf("select item_id, ym, customer_id, min(rental_date) rental_date
    from DF 
    group by item_id, ym")

这种情况的结果是:

  item_id      ym customer_id      rental_date
1    I001 2012-09           4       2012-09-30
2    I001 2012-10           6       2012-10-11
3    I002 2012-09           5       2012-09-15
4    I002 2012-10           4       2012-10-05
5    I004 2012-10          10       2012-10-13

答案 1 :(得分:2)

我假设您示例中的对象是data.frame,我们称之为df

library( "plyr" )
df$rental_date <- as.Date( df$rental_date, "%m/%d/%Y" )
df$year <-  as.numeric( format( df$rental_date, "%Y"))
df$month <- months( df$rental_date )

ddply( df, c("item_id", "month", "year"), function(x) {
  x[ min(x$rental_date) == x$rental_date, "customer_id", drop=FALSE ]
} )

结果如下:

  item_id     month year customer_id
1    I001   October 2012           6
2    I001 September 2012           4
3    I002   October 2012           4
4    I002 September 2012           5
5    I004   October 2012          10