3

我有一个data.frame

ID  code
A    1
A    1
A    2
A    1
B    4
B    1
B    1
C    2
C    3
C    3
C    2

我知道如何删除,但我必须计算频率:

ID  code  freq
A    1     3
A    2     1
B    4     1
B    1     2
C    2     2
C    3     2
4

2 回答 2

2

有几种方法。这是一个使用ave

unique(within(mydf, {
  Freq <- ave(code, ID, code, FUN = length)
}))
#   ID code Freq
# 1  A    1    3
# 3  A    2    1
# 5  B    4    1
# 6  B    1    2
# 8  C    2    2
# 9  C    3    2

或者,另一种选择(但行顺序不同):

X <- data.frame(table(mydf))
X[X$Freq != 0, ]
#    ID code Freq
# 1   A    1    3
# 2   B    1    2
# 4   A    2    1
# 6   C    2    2
# 9   C    3    2
# 11  B    4    1

更新

如果您愿意使用包(此答案中的其他两个选项使用 base R),您应该检查“data.table”,特别是如果您的数据很大:

library(data.table)
DT <- data.table(mydf)
DT[, .N, by = c("ID", "code")]
#    ID code N
# 1:  A    1 3
# 2:  A    2 1
# 3:  B    4 1
# 4:  B    1 2
# 5:  C    2 2
# 6:  C    3 2

基准

以下是更大数据集的一些基准,以了解选项如何扩展。

library(microbenchmark)
library(data.table)

补一些数据:

set.seed(1)
mydf <- data.frame(ID = sample(LETTERS, 100000, replace = TRUE), 
                   code = sample(1:10, 100000, replace = TRUE))
DT <- data.table(mydf)

建立你的功能:

AM1 <- function() {
  X <- data.frame(table(mydf))
  X[X$Freq != 0, ]
}

AM2 <- function() {
  unique(within(mydf, {
    Freq <- ave(code, ID, code, FUN = length)
  }))
}

AM3 <- function() {
  DT[, .N, by = c("ID", "code")]
}

DDP <- function() {
  ddply(mydf, .(ID, code), nrow)
}

基准:

microbenchmark(AM1(), AM2(), AM3(), DDP(), times=100)
# Unit: milliseconds
#   expr       min        lq    median        uq       max neval
# AM1()  65.64750  66.92666  68.86916  70.25277 137.12961   100
# AM2() 224.85660 228.05091 230.02311 232.77116 295.55184   100
# AM3()  11.15789  11.30541  11.44706  11.72064  77.72398   100
# DDP()  97.75484 100.86891 103.42602 106.85045 171.02863   100

在小型数据集上(您可以尝试一下),AM2()应该是最快的,但它不能很好地扩展,如上面的结果所示。AM3(),但是,(“data.table”选项)将很难处理更大的数据集。

于 2013-04-28T06:17:51.933 回答
2

ddplyplyr包装中使用。

library(plyr)
dfDuplicates = as.data.frame(read.table(textConnection("ID  code
A    1
A    1
A    2
A    1
B    4
B    1
B    1
C    2
C    3
C    3
C    2"), header = TRUE))

ddply(dfDuplicates, .(ID, code), nrow)
于 2013-04-28T06:30:04.803 回答