如何为嵌套矩阵匹配和colSums加快R中的for循环

Fed*_*rgi 5 performance for-loop r

我有一个看似很简单的问题,与之相比,我需要更快的R实现。

我为此示例初始化随机种子和尺寸:

set.seed(1)
d1<-400
d2<-20000
d3<-50
Run Code Online (Sandbox Code Playgroud)

我有一个矩阵X,尺寸为d1 x d2

X<-as.data.frame(matrix(rnorm(d1*d2),nrow=d1,ncol=d2))
rownames(X)<-paste0("row",1:nrow(X))
colnames(X)<-paste0("col",1:ncol(X))
Run Code Online (Sandbox Code Playgroud)

以及具有d1行索引的向量u :

u<-sample(rownames(X),nrow(X),replace=TRUE)
Run Code Online (Sandbox Code Playgroud)

我也有一个矩阵C,其命名的行和尺寸为d3 x d2

C<-matrix(rnorm(d3*d2),nrow=d3,ncol=d2)
rownames(C)<-sample(rownames(X),nrow(C),replace=FALSE)
Run Code Online (Sandbox Code Playgroud)

现在,通过以下非常慢的循环,我用匹配的X行的总和填充矩阵C:

system.time(
    for(i in 1:nrow(C)){
        indexes<-which(u==rownames(C)[i])
        C[i,] <- colSums(X[indexes,])
    }
)
Run Code Online (Sandbox Code Playgroud)

在我的PC上,此操作大约需要11.5秒,但是我确信可以通过避免for循环来加快速度。有任何想法吗?非常感谢!

min*_*nem 3

matrixStats::colSums2只需与选项一起使用即可传递行索引并移出rownames()循环(X需要转换为矩阵):

Xm <- as.matrix(X)
names_of_rows <- rownames(C)
system.time(for (i in 1:nrow(C)) {
  indexes <- which(u == names_of_rows[i])
  C[i, ] <-  matrixStats::colSums2(Xm, rows = indexes)
})
# 0.03 sek
Run Code Online (Sandbox Code Playgroud)

  • 到目前为止,所有解决方案都很漂亮,但这个解决方案是完美的。加速超过 100 倍。谢谢你,我的,你帮了很大的忙。 (2认同)