I have a matrix in which I want to zero certain specific elements.
For instance, imagine that my matrix is:
m <- matrix(1:100, ncol=10)
I then have two vectors indicating which elements to keep
m.from <- c(2, 5, 4, 4, 6, 3, 1, 4, 2, 5)
m.to <- c(7, 9, 6, 8, 9, 5, 6, 8, 4, 8)
So, for instance I will keep elements 3:6 in row 1, and set element 1:2 and 7:10 to 0. For line 2 I will keep 6:8 and zero the rest, and so on.
Now, I could easily do:
for (line in 1:nrow(m))
{
m[line, 1:m.from[line]] <- 0
m[line, m.to[line]:ncol(m)] <- 0
}
which gives the correct result.
In my specific case, however, I am operating on a ~15000 x 3000 matrix which makes using this kind of loop excruciatingly long.
How can I speed up this code? I though of using apply
, but how do I access the correct index of m.from and m.to?
Here's a simple matrix oriented solution:
m[col(m) <= m.from] <- 0
m[col(m) >= m.to] <- 0
m
[,1] [,2] [,3] [,4] [,5] [,6] [,7] [,8] [,9] [,10]
[1,] 0 0 21 31 41 51 0 0 0 0
[2,] 0 0 0 0 0 52 62 72 0 0
[3,] 0 0 0 0 43 0 0 0 0 0
[4,] 0 0 0 0 44 54 64 0 0 0
[5,] 0 0 0 0 0 0 65 75 0 0
[6,] 0 0 0 36 0 0 0 0 0 0
[7,] 0 17 27 37 47 0 0 0 0 0
[8,] 0 0 0 0 48 58 68 0 0 0
[9,] 0 0 29 0 0 0 0 0 0 0
[10,] 0 0 0 0 0 60 70 0 0 0
(I think I might win the R Golf prize on this one , too.) For which my entry would be:
m[col(m)<=m.from|col(m)>= m.to]<-0
If you love us? You can donate to us via Paypal or buy me a coffee so we can maintain and grow! Thank you!
Donate Us With