[R] matrix row product and cumulative product
Charles C. Berry
cberry at tajo.ucsd.edu
Mon Aug 18 05:35:54 CEST 2008
On Sun, 17 Aug 2008, Jeff Laake wrote:
> I spent a lot of time searching and came up empty handed on the following
> query. Is there an equivalent to rowSums that does product or cumulative
> product and avoids use of apply or looping? I found a rowProd in a package
> but it was a convenience function for apply. As part of a likelihood
> calculation called from optim, I’m computing products and cumulative products
> of rows of matrices with far more rows than columns. I started with apply and
> after some thought realized that a loop of columns might be faster and it was
> substantially faster (see below). Because the likelihood function is called
> many times I’d like to speed it up even more if possible.
You might check out the 'inline' or 'jit' packages.
Otherwise, if you can as easily treat xmat as a list (or
data.frame),
Reduce( "*", xmat.data.frame, accumulate=want.cumprod )
(where want.cumprod is FALSE for product, TRUE for cumulative product)
will be a bit faster in many circumstances. However, this advantage is
lost if you must retain xmat as a matrix since converting it to a
data.frame seems to require more time than you save.
HTH,
Chuck
>
> Below is an example showing the cumprod.matrix and prod.matrix looping
> functions that I wrote and some timing comparisons to the use of apply for
> different column and row dimensions. At this point I’m better off with
> looping but I’d like to hear of any further suggestions.
>
> Thanks –jeff
>
>> prod.matrix=function(x)
> + {
> + y=x[,1]
> + for(i in 2:dim(x)[2])
> + y=y*x[,i]
> + return(y)
> + }
>
>> cumprod.matrix=function(x)
> + {
> + y=matrix(1,nrow=dim(x)[1],ncol=dim(x)[2])
> + y[,1]=x[,1]
> + for (i in 2:dim(x)[2])
> + y[,i]=y[,i-1]*x[,i]
> + return(y)
> + }
>
>> N=10000000
>> xmat=matrix(runif(N),ncol=10)
>> system.time(cumprod.matrix(xmat))
> user system elapsed
> 1.07 0.09 1.15
>> system.time(t(apply(xmat,1,cumprod)))
> user system elapsed
> 29.27 0.21 29.50
>> system.time(prod.matrix(xmat))
> user system elapsed
> 0.29 0.00 0.30
>> system.time(apply(xmat,1,prod))
> user system elapsed
> 30.69 0.00 30.72
>> xmat=matrix(runif(N),ncol=100)
>> system.time(cumprod.matrix(xmat))
> user system elapsed
> 1.05 0.13 1.18
>> system.time(t(apply(xmat,1,cumprod)))
> user system elapsed
> 3.55 0.14 3.70
>> system.time(prod.matrix(xmat))
> user system elapsed
> 0.38 0.01 0.39
>> system.time(apply(xmat,1,prod))
> user system elapsed
> 2.87 0.00 2.89
>> xmat=matrix(runif(N),ncol=1000)
>> system.time(cumprod.matrix(xmat))
> user system elapsed
> 1.30 0.18 1.46
>> system.time(t(apply(xmat,1,cumprod)))
> user system elapsed
> 1.77 0.27 2.05
>> system.time(prod.matrix(xmat))
> user system elapsed
> 0.46 0.00 0.47
>> system.time(apply(xmat,1,prod))
> user system elapsed
> 0.7 0.0 0.7
>> xmat=matrix(runif(N),ncol=10000)
>> system.time(cumprod.matrix(xmat))
> user system elapsed
> 1.28 0.00 1.29
>> system.time(t(apply(xmat,1,cumprod)))
> user system elapsed
> 1.19 0.08 1.26
>> system.time(prod.matrix(xmat))
> user system elapsed
> 0.40 0.00 0.41
>> system.time(apply(xmat,1,prod))
> user system elapsed
> 0.57 0.00 0.56
>> xmat=matrix(runif(N),ncol=100000)
>> system.time(cumprod.matrix(xmat))
> user system elapsed
> 3.18 0.00 3.19
>> system.time(t(apply(xmat,1,cumprod)))
> user system elapsed
> 1.42 0.21 1.64
>> system.time(prod.matrix(xmat))
> user system elapsed
> 1.05 0.00 1.05
>> system.time(apply(xmat,1,prod))
> user system elapsed
> 0.82 0.00 0.81
>> R.Version()
> $platform
> [1] "i386-pc-mingw32"
> .
> .
> .
> $version.string
> [1] "R version 2.7.1 (2008-06-23)"
>
> ______________________________________________
> R-help at r-project.org mailing list
> https://stat.ethz.ch/mailman/listinfo/r-help
> PLEASE do read the posting guide http://www.R-project.org/posting-guide.html
> and provide commented, minimal, self-contained, reproducible code.
>
Charles C. Berry (858) 534-2098
Dept of Family/Preventive Medicine
E mailto:cberry at tajo.ucsd.edu UC San Diego
http://famprevmed.ucsd.edu/faculty/cberry/ La Jolla, San Diego 92093-0901
More information about the R-help
mailing list