在数据框中获取前n行的数据?

6

I have the following data frame.

date id value
2012-01-01 1 0.3
2012-01-01 2 0.5
2012-01-01 3 0.2
2012-01-01 4 0.8
2012-01-01 5 0.2
2012-01-01 6 0.8
2012-01-01 7 0.1
2012-01-01 8 0.4
2012-01-01 9 0.3
2012-01-01 10 0.2

有几个日期,每个日期都有10个ID值和一个值字段。我想要做的是对于每个ID找到“value”字段中的前n个值。例如,如果n = 3,则输出应如下所示。

date id value value1 value2 value3
2012-01-01 1 0.3 NA NA NA
2012-01-01 2 0.5 NA NA NA
2012-01-01 3 0.2 NA NA NA
2012-01-01 4 0.8 0.2 0.5 0.3
2012-01-01 5 0.2 0.8 0.2 0.5
...

是否有一种简单的方法可以通过plyr或使用mapply轻松实现这一点?非常感谢您提前的帮助。

3个回答

6

您可以使用基本函数轻松完成此操作:

id <- 1:10
value <- c(0.3,0.5,0.2,0.8,0.2,0.8,0.1,0.4,0.3,0.2)
test <- data.frame(id,value)

test$valprev1 <- c(rep(NA,1),head(test$value,-1))
test$valprev2 <- c(rep(NA,2),head(test$value,-2))
test$valprev3 <- c(rep(NA,3),head(test$value,-3))

结果

   id value valprev1 valprev2 valprev3
1   1   0.3       NA       NA       NA
2   2   0.5      0.3       NA       NA
3   3   0.2      0.5      0.3       NA
4   4   0.8      0.2      0.5      0.3
5   5   0.2      0.8      0.2      0.5
6   6   0.8      0.2      0.8      0.2
7   7   0.1      0.8      0.2      0.8
8   8   0.4      0.1      0.8      0.2
9   9   0.3      0.4      0.1      0.8
10 10   0.2      0.3      0.4      0.1

之前在这里犯了一个错误 - 这是一个使用sapply函数的版本:
prevrows <- function(data,n) {sapply(1:n,function(x) c(rep(NA,x),head(data,-x)))}
prevrows(test$value,3)

这只会生成这个:

      [,1] [,2] [,3]
 [1,]   NA   NA   NA
 [2,]  0.3   NA   NA
 [3,]  0.5  0.3   NA
 [4,]  0.2  0.5  0.3
 [5,]  0.8  0.2  0.5
 [6,]  0.2  0.8  0.2
 [7,]  0.8  0.2  0.8
 [8,]  0.1  0.8  0.2
 [9,]  0.4  0.1  0.8
[10,]  0.3  0.4  0.1

你可以将此应用于数据中的每组日期,如下所示:
result <- tapply(test$value,test$date,prevrows,3)

这提供了每个日期集的一堆列表。您可以使用rowbind将它们连接起来,然后添加回您的数据集中:

data.frame(test,do.call(rbind,result))

看起来不错。喜欢tapply/sapply和do.call函数式方法提供的简洁性。仍在努力让自己思考这些方法。 - broccoli

3

使用 data.table v1.9.5+,这非常简单:

library(data.table)
setDT(dt)

lags <- dt[, shift(value, n = c(1,2,3))]

或将它们附加为同一数据表中的额外列:
dt[, c("lag1", "lag2", "lag3") := shift(value, n = c(1,2,3))]

0

只是想为@thelatemail的答案增加一些内容(由于我的声望无法直接评论):

prevrows2 <- function(data,n) {
if (length(data) >= 10){
sapply(1:n,function(x) c(rep(NA,x),head(data,-x)))
} else {
cbind(sapply(1:length(data),function(x) c(rep(NA,x),head(data,-x))),
matrix(NA,nrow = length(data),ncol= n - length(data)))}
}

这个补充可以防止在一个组中的行数少于你想选择的行数(n)的情况。


网页内容由stack overflow 提供, 点击上面的
可以查看英文原文,
原文链接