2

我正在使用 R,我想创建一个显示序列或排名的列,同时按两个因素(hhid 和 period)分组。

例如,我有这个数据集:

hhid perid
1000 1     
1000 1
1000 1
1000 2
1000 2
2000 1
2000 1
2000 1
2000 1
2000 2
2000 2

我想像这样添加一个名为“actno”的列:

hhid perid actno
1000 1     1
1000 1     2
1000 1     3
1000 2     1
1000 2     2
2000 1     1
2000 1     2
2000 1     3
2000 1     4
2000 2     1
2000 2     2
4

5 回答 5

4

如果您有很多组或大量数据,data.table这是提高时间和内存效率的方法

# assuming your data is in a data.frame called DF
library(data.table)
DT <- data.table(DF)


DT[, ActNo := seq_len(.N), by = list(hhid,perid)]

请注意,.N通过分组给出子集中的行数(?data.table有关详细信息,请参阅)

于 2012-09-12T00:24:46.423 回答
3

不需要 plyr。只需使用aveseq

> dat$actno <- with( dat, ave(hhid, hhid, perid, FUN=seq))
> dat
   hhid perid actno
1  1000     1     1
2  1000     1     2
3  1000     1     3
4  1000     2     1
5  1000     2     2
6  2000     1     1
7  2000     1     2
8  2000     1     3
9  2000     1     4
10 2000     2     1
11 2000     2     2

这个例子中的第一个参数可以是 column 或者你可以用稍微不那么优雅的 bu 来做,也许更清楚:

dat$actno <- with( dat, ave(hhid, hhid, perid, FUN=function(x) seq(length(x) ) ) )
于 2012-09-11T21:43:45.890 回答
2

如果您的数据被调用urdat,那么plyr您可以执行以下操作:

df <- urdat[order(urdat$hhid, urdat$perid),]
df$actno <- sequence(rle(df$perid)$lengths)
于 2012-09-11T21:14:27.283 回答
1

plyr软件包可以很好地做到这一点:

library(plyr)
dat <- structure(list(hhid = c(1000L, 1000L, 1000L, 1000L, 1000L, 2000L, 
2000L, 2000L, 2000L, 2000L, 2000L), perid = c(1L, 1L, 1L, 2L, 
2L, 1L, 1L, 1L, 1L, 2L, 2L)), .Names = c("hhid", "perid"), class = "data.frame", row.names = c(NA, 
-11L))

ddply(dat, .(hhid, perid), transform, actno=seq_along(perid))

   hhid perid actno
1  1000     1     1
2  1000     1     2
3  1000     1     3
4  1000     2     1
5  1000     2     2
6  2000     1     1
7  2000     1     2
8  2000     1     3
9  2000     1     4
10 2000     2     1
11 2000     2     2
于 2012-09-11T20:34:43.457 回答
-4

伪代码:

For each unique value of `hhid` `h`
    For each unique value of `perid` `p`
        counter = 0;
        For each row of table where `hhid==h && perid==p`
            counter++;
            Assign counter to `actno` of this column

应该很容易实现,尤其是使用数据框

于 2012-10-06T21:04:26.007 回答