What is the fastest way to extract the min from each column in a matrix?
EDIT:
Moved all the benchmarks to the answer below.
Using a Tall, Short or Wide Matrix:
## TEST DATA
set.seed(1)
matrix.inputs <- list(
"Square Matrix" = matrix(sample(seq(1e6), 4^2*1e4, T), ncol=400), # 400 x 400
"Tall Matrix" = matrix(sample(seq(1e6), 4^2*1e4, T), nrow=4000), # 4000 x 40
"Wide-short Matrix" = matrix(sample(seq(1e6), 4^2*1e4, T), ncol=4000), # 40 x 4000
"Wide-tall Matrix" = matrix(sample(seq(1e6), 4^2*1e5, T), ncol=4000), # 400 x 4000
"Tiny Sq Matrix" = matrix(sample(seq(1e6), 4^2*1e2, T), ncol=40) # 40 x 40
)
Update 2014-12-17:
colMins()
et al. were made significantly faster in a recent version of matrixStats. Here's an updated benchmark summary using matrixStats 0.12.2 showing that it ("cmin") is ~5-20 times faster than the second fastest approach:Previous comment 2013-10-09:
FYI, since matrixStats v0.8.7 (2013-07-28),
colMins()
is roughly twice as fast as before. The reason is that the function previously utilizedcolRanges()
, which explains the "surprisingly slow" results reported here. Same speed is seen forcolMaxs()
,rowMins()
androwMaxs()
.mat[(1:ncol(mat)-1)*nrow(mat)+max.col(t(-mat))]
seems pretty fast, and it's base R.The
sos
package is great for answering these sorts of questions.http://finzi.psych.upenn.edu/R/library/matrixStats/html/rowRanges.html
Oddly enough, for the one example I tried
colMins
was slower. Perhaps someone can point out what's funny about my example?Below is a collection of the answers thus far. This will be updated as more answers are contributed.
BENCHMARKS
Here is one that is faster on square and wide matrices. It uses
pmin
on the rows of the matrix. (If you know a faster way of splitting the matrix into its rows, please feel free to edit)Using the same benchmark as @RicardoSaporta: