为了加快速度,特别是如果您只需要df$V2
在 的基础上拆分,df$V1
请在调用中仅使用该向量而split
不是整个数据帧df
。例如:
## Dummy data
df <- read.table(text = "V1 V2
A1BG A1BG
A1BG CRISP3
A1CF A1CF
A1CF APOBEC1
A1CF CUGBP2
A1CF KHSRP", header = TRUE)
## make it big!
df <- with(df, cbind.data.frame(V1 = rep(V1, length.out = 1e5),
V2 = rep(V2, length.out = 1e5)))
# time it
system.time(sp1 <- split(df, df$V1))
system.time(sp2 <- split(df$V2, df$V1))
> system.time(sp1 <- split(df, df$V1))
user system elapsed
0.024 0.000 0.016
> system.time(sp2 <- split(df$V2, df$V1))
user system elapsed
0.008 0.000 0.005
这是一个级别很少的示例。对于非常多的级别,拆分整个数据帧的低效率开始严重影响计算时间,例如对于大约 10000 个级别的因子:
df2 <- data.frame(V1 = factor(sample(10000, 1e5, replace = TRUE)),
V2 = rnorm(1e5))
system.time(sp3 <- split(df2, df2$V1))
system.time(sp4 <- split(df2$V2, df2$V1))
> system.time(sp3 <- split(df2, df2$V1))
user system elapsed
5.332 0.000 4.216
>
> system.time(sp4 <- split(df2$V2, df2$V1))
user system elapsed
0.008 0.000 0.005
这样做的原因是,在这种split(df, df$V1)
情况下,该split.data.frame
方法被调用,该方法lapply()
对向量本身执行一个由( )1:nrow(df)
分成组的方法,并将一个函数 ( ) 应用于每个组件。因此,随着级别数量的增加,对该匿名函数的函数调用次数也会增加并增加计算时间。f
df$V2
function(ind) x[ind, , drop = FALSE])
在使用方法的split(df$V2, df$v1)
情况下split.default
,如果使用 factor 调用,f
基本上只需要调用split
. 因此,它不会产生任何调用匿名函数的开销,也不会重复调用[
.