# What’s that “pre- and post-multiply” stuff?

January 5, 2013
By

(This article was first published on Industrial Code Workshop, and kindly contributed to R-bloggers)

Often in SEM scripts you will see matrices being pre- and post-multiplied by some other matrix. For instance, this figures in scripts computing the genetic correlation between variables. How does pre- and post-multiplying a variance/covariance matrix give us a correlation matrix? And what is it that we are multiplying this matrix by?

In general, a covariance matrix can be converted to a correlation matrix by pre- and post-multiplying by a diagonal matrix with 1/SD for each variable on the diagonal.
In R, matrix inversion (usually signified by A -1) is done using the solve() function.
For the diagonal case, the inverse of a matrix is simply 1/x in each cell.

## Example with variance matrix A

`` A = matrix(nrow = 3, byrow = T,c(   1,0,0,   0,2,0,  0,0,3) );  solve(A)      [,1] [,2]  [,3] [1,]    1  0.0  0.00 [2,]    0  0.5  0.00 [3,]    0  0.0  0.33``
A number times its inverse = 1. For Matrices `solve(A) %*% A = Identity Matrix`
``solve(A) %*% A #  = I: The Standardized diagonal matrix     [,1] [,2] [,3][1,]    1    0    0[2,]    0    1    0[3,]    0    0    1``

### An example with values (covariances) in the off-diagonals

``A = matrix(nrow = 3, byrow = T, c(    1, .5, .9,  .5,  2, .4, .9, .4,  4));I = matrix(nrow = 3, byrow = T, c(  1,  0, 0,  0,  1, 0, 0,  0, 1)); varianceA = I * A # zero the off-diagonal (regular, NOT matrix multiplication)sdMatrix  = sqrt(varianceA) # element sqrt to get SDs on diagonal: SD=sqrt(var)invSD     = solve(sdMatrix) # 1/SD = inverse of sdMatrixinvSD     [,1] [,2] [,3][1,]    1 0.00  0.0[2,]    0 0.71  0.0[3,]    0 0.00  0.5``
Any number times its inverse = 1, so this sweeps covariances into correlations
``corr = invSD %*% A %*% invSD # pre- and post- multiply by 1/SD     [,1] [,2] [,3][1,] 1.00 0.35 0.45[2,] 0.35 1.00 0.14[3,] 0.45 0.14 1.00``

## Easy way of doing this in R

Using diag to grab the diagonal and make a new one, and capitalising on the fact that inv(X) = 1/x for a diagonal matrix
``diag(1/sqrt(diag(A))) %&% A # The %&% is a shortcut to pre- and post-mul     [,1] [,2] [,3][1,] 1.00 0.35 0.45[2,] 0.35 1.00 0.14[3,] 0.45 0.14 1.00``

## Even-easier built-in way

``cov2cor(A)     [,1] [,2] [,3][1,] 1.00 0.35 0.45[2,] 0.35 1.00 0.14[3,] 0.45 0.14 1.00``Note: See also this followup post on getting a correlation matrix when you are starting with a lower-triangular Cholesky composition.``

R-bloggers.com offers daily e-mail updates about R news and tutorials on topics such as: Data science, Big Data, R jobs, visualization (ggplot2, Boxplots, maps, animation), programming (RStudio, Sweave, LaTeX, SQL, Eclipse, git, hadoop, Web Scraping) statistics (regression, PCA, time series, trading) and more...

If you got this far, why not subscribe for updates from the site? Choose your flavor: e-mail, twitter, RSS, or facebook...

## Recent popular posts

Contact us if you wish to help support R-bloggers, and place your banner here.

# Never miss an update! Subscribe to R-bloggers to receive e-mails with the latest R posts.(You will not see this message again.)

Click here to close (This popup will not appear again)