问题
是否可以知道哪个是效率最高的data.table
'加入'在执行加入之前使用?
这样做的目的是在公共密钥dt1
上加入两个表dt2
和alpha
,其中dt1$beta <= dt2$beta
。两个示例表:
# dt1 dt2
# id alpha beta alpha beta
# 1: 35 A 284 1: A 478
# 2: 74 A 916 2: A 1034
# --- ---
# 9999: 9967 Z 483 9999: Z 303
# 10000: 9988 Z 473 10000: Z 1411
可能是non-equi
加入,实施时会解决这个问题,但是现在我想知道是否有办法从两个表的大小告诉最好的方法使用
在示例中,最快的&#39;方法根据表的大小而变化。它们也代表了我的实际数据,这些数据会定期更改,因此我希望编写一个使用“最佳”数据的函数。加入。
实施例
在这里,我设置了一些功能来创建数据,执行几个连接并运行基准测试。基准测试在三个不同大小的表上运行
library(data.table)
library(microbenchmark)
## Function to create data.tables
fun_create_data <- function(s1, s2){
set.seed(123) ## keep consistency
dt1 <- data.table(id = seq(1:s1),
alpha = sample(LETTERS, size=s1, replace=T),
beta = sample(1:1440, size=s1, replace=T))
dt2 <- data.table(alpha = sample(LETTERS, size=s2, replace=T),
beta = sample(1:1440, size=s2, replace=T))
setkey(dt1, alpha)
setkey(dt2, alpha)
return(lst = list(dt1, dt2))
}
我使用的联接是
## inner join, allow.cartesian = TRUE,
## then filtering out results after the join
fun_join_cartesian <- function(dt1, dt2){
dt1[ dt2, nomatch=0, allow.cartesian=TRUE][beta <= i.beta]
}
## join using i.col (specifying criteria for each i.)
fun_join_eachi <- function(dt1, dt2){
dt1[ dt2, {
idx = beta <= i.beta
.(id = id[idx],
beta = beta[idx],
i.beta = i.beta)
},
by=.EACHI
][!is.na(id)]
}
基准功能
fun_mb <- function(dt1, dt2){
microbenchmark(
fun_join_cartesian(dt1, dt2),
fun_join_eachi(dt1, dt2),
times=10
)
}
fisrt示例使笛卡尔联接表现最佳
s1 <- 1000
s2 <- s1
lst <- fun_create_data(s1, s2)
dt1 <- lst[[1]]
dt2 <- lst[[2]]
fun_mb(dt1, dt2)
# Unit: milliseconds
# expr min lq mean median uq max neval
# fun_join_cartesian(dt1, dt2) 1.727606 1.741692 1.785893 1.770675 1.778107 1.986325 10
# fun_join_eachi(dt1, dt2) 3.490216 3.518185 3.593305 3.559949 3.662209 3.826939 10
第二个例子也有笛卡尔连接表现最佳
s1 <- 1000
s2 <- s1 * 5
lst <- fun_create_data(s1, s2)
dt1 <- lst[[1]]
dt2 <- lst[[2]]
fun_mb(dt1, dt2)
# Unit: milliseconds
# expr min lq mean median uq max neval
# fun_join_cartesian(dt1, dt2) 5.690791 5.70429 6.433174 5.923583 6.19849 10.84091 10
# fun_join_eachi(dt1, dt2) 12.153050 12.47688 13.469481 12.711631 13.46108 18.71149 10
而第三个示例的eachi
联接表现最佳
s1 <- 10000
s2 <- s1
lst <- fun_create_data(s1, s2)
dt1 <- lst[[1]]
dt2 <- lst[[2]]
fun_mb(dt1, dt2)
# Unit: milliseconds
# expr min lq mean median uq max neval
# fun_join_cartesian(dt1, dt2) 170.16523 171.33960 185.9685 173.3784 175.3022 299.5541 10
# fun_join_eachi(dt1, dt2) 88.17374 95.48863 138.8535 155.7180 161.2675 162.1637 10