系统:
操作系统 - Windows 7
内存 - 8GB
处理器 - Intel i7
R 版本 - 始终保持最新
问题:
R 仅使用我的英特尔 i7 处理器的 13%(即 8 个核心中的 1 个)。我想利用多个核心来更快地运行我的代码。但不幸的是无法。
尝试:
开始使用 Parallel、Snow、Snowfall 包,甚至将它们配置为使用 8 个核心,但不幸的是,我没有使用任何 apply 函数来利用它们提供的自定义函数(如 mcapply、sflapply)。
for (i in 1:number.of.accounts){
if (is.na(s$rev2012[i]) == "FALSE" && is.na(s$rev2013[i]) == "TRUE"){
loss = rbind(loss, s[i,])
}
x = x + 1
}
上述代码中的数据框“s”大约有 56,000 行 14 列。 “rev”代表收入。我想做的是,如果 2012 年有收入,但 2013 年没有,那么我们就“失去”了那个客户。我使用“x”来计算速度。
这段代码需要大量时间来运行,而我还没有让它完成。当我打断时,我发现进展不大。
任何解锁所有核心以运行这段代码的帮助都会非常好。
谢谢!
您的代码实际上有两个问题。首先,您使用 for 循环逐行求值。在 R 中,几乎没有任何情况这是好的做法。其次,您一次向
loss
追加一行。这也非常慢。
使用并行处理最多可提供 8 倍的改进。矢量化将提供超过 50 倍的改进,使用
data.tables
将进一步改进。
df <- data.frame(rev2012=sample(c(NA,1:99),56000,replace=T),
rev2013=sample(c(NA,1:99),56000,replace=T))
df <- cbind(df,matrix(rnorm(56000*12),ncol=12))
for.loop <- function(){
loss <- c()
for (i in 1:nrow(df))
if (is.na(df$rev2012[i]) == "FALSE" && is.na(df$rev2013[i]) == "TRUE") loss = rbind(loss, df[i,])
}
df.vectorized <- function(){
loss <- with(df,df[!is.na(rev2012) & is.na(rev2013),])
}
library(data.table)
dt <- function(){
dt <- data.table(df)
setkey(dt,rev2012,rev2013)
loss <- dt[!is.na(rev2012)&is.na(rev2013)]
}
library(microbenchmark)
microbenchmark(for.loop(),df.vectorized(),dt(),times=10)
# Unit: milliseconds
# expr min lq median uq max neval
# for.loop() 3141.53686 3431.99529 3620.90536 3845.81394 3875.92435 10
# df.vectorized() 38.76076 55.01082 58.97976 64.19538 67.33192 10
# dt() 28.20870 31.10005 40.54224 165.20777 184.48776 10
数据表仅比矢量化数据框方法提高了约 33% 的原因是 56,000 行并没有那么大。如果
df
有 >1e6 行,使用 data.table
肯定是最好的选择。