我有一个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
我有一个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
有几种方法。这是一个使用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”选项)将很难处理更大的数据集。
ddply
从plyr
包装中使用。
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)