Question

My brain must not be too sharp this Friday afternoon. In the example from the lower.tri() function in R http://stat.ethz.ch/R-manual/R-patched/library/base/html/lower.tri.html, you can turn all lower triangular elements of a matrix into NA as follows.

(m2 <- matrix(1:20, 4, 5))
lower.tri(m2)
m2[lower.tri(m2)] <- NA 
m2

Rather than write over the existing m2 object, how would I save the result in a new object, say m3?

I tried:

m3 <- m2[lower.tri(m2)] <- NA
m3

This returns NA

I can get the result I want by wrapping the whole thing in a function.

lower.tri.na <- function(m2) {
m2[lower.tri(m2)] <- NA
return(m2)
}
m3 <- lower.tri.na(m2)
m3

This code below worked too (but I really wanted to use the lower.tri() function):

m3 <- ifelse(row(m2) > col(m2), NA, m2)

Is there a better (more efficient) way?...my guess is yes. (and dumb question why doesn't this code or style of assingment work m3 <- m2[lower.tri(m2)] <- NA). Thanks in advance.

Was it helpful?

Solution

The easiest answer is

m3<-m2
m3[lower.tri(m3)] <- NA

Or you can do

m3<-`[<-`(m2, lower.tri(m2), NA)

which looks very awkward but it works. You're basically intercepting the value that from []<-what would normally replace the variable in the assignment and sending it to a new variable.\

And your strategy of m3 <- m2[lower.tri(m2)] <- NA doesn't work because when you do a <- b <- c that's the same as a <- (b <- c) which is the same as a <-c; b<-c because the assignment operator generally passes along what was on the right side of the equation. So you're just doing m3<-NA. There is a special operator for matrices called [<- that will reshape that NA to an appropriate size for it's dimensions based on what you supply as an index. But here, you are not using [] on the m3 so you are not getting that special behavior

Licensed under: CC-BY-SA with attribution
Not affiliated with StackOverflow
scroll top