R语言计算MLE的嵌套循环运行过慢,如何优化代码效率
R三层嵌套循环优化方案
下面针对你的MLE计算循环,给出几个可落地的优化方向,优化后速度通常可以提升10~100倍:
预计算所有不变量,避免循环内重复计算
你代码里有大量和循环索引无关的计算,全部移到循环外提前算完:- 和t、c无关的项:
exp_LAN2 <- exp(-LAN2 * dt),长度为n的向量 - 和t无关的项:
X_term是n行C列的矩阵,对应每个k、c的正态项计算:X_term <- matrix(0, nrow = n, ncol = C) for (c in 1:C) { X_term[, c] <- exp(alpha[c]) * exp(-(X - mx[c])^2 / (2 * sx[c]^2)) } - 和k无关的项:
mvn_term是tj行C列的矩阵,对应每个t、c的多元正态密度计算,这里用优化过的mvtnorm::dmvnorm替代原有慢实现:library(mvtnorm) mvn_term <- matrix(0, nrow = tj, ncol = C) for (c in 1:C) { # 直接向量化计算所有t对应c类的mvn密度,不用逐t循环 mvn_term[, c] <- dt * dmvnorm(m, mean = mu[[c]], sigma = sig[[c]]) }
- 和t、c无关的项:
用矩阵运算完全替代嵌套循环
原来的三层循环可以直接简化为几行代码,完全消除k、c层的显式循环:# 先初始化所有行都为S[t]=0时的取值 l <- matrix(exp_LAN2, nrow = tj, ncol = n, byrow = TRUE) # 只更新S[t]==1的行,用矩阵乘法完成c维度的求和 s1_idx <- which(S == 1) l[s1_idx, ] <- exp_LAN2 * (mvn_term[s1_idx, ] %*% t(X_term))进阶优化(超大规模参数时用)
如果n和tj超过10万,还可以用Rcpp把整个逻辑编译为C++代码运行,速度会比纯R向量化再提升一个数量级,也可以进一步对X_term和mvn_term的计算做并行化处理。
内容的提问来源于stack exchange,提问作者Rade math
相关产品推荐
相关产品推荐

