You are here

Constraining parameters using mxAlgebra bracket notation

3 posts / 0 new
Last post
bwiernik's picture
Offline
Joined: 01/30/2014 - 19:39
Constraining parameters using mxAlgebra bracket notation

I have model specified in RAM notation where'd I'd like to constrain some parameters using mxAlgebra.

Here is the script:

circumplex <- umxRAM("circumplex", data=mxData(mat[vars,vars],type="cov",numObs=N),
                              umxPath(var = vars, fixedAt=0),
                              umxPath(var = latentvars, labels=paste("communal",vars,sep="")),
                              umxPath(latentvars, to=vars, values=.6, labels=paste("scaling",vars,sep="")),
 
                              mxMatrix("Full", nrow=k1, ncol=1, free=TRUE, values=startAngles, labels=angles, name="Angles"),
                              mxAlgebra(cos(Angles), name="COS"),
                              mxAlgebra(sin(Angles), name="SIN"),
 
                              umxPath("gamma", to=latentvars, fixedAt=1, labels=paste("gamma",vars,sep="")),
                              umxPath("Fc", to=latentvars[1], fixedAt=1, labels=paste("Fc",latentvars[1],sep="")),
                              umxPath("Fc", to=latentvars[-1], free=FALSE, #values=startloadingsC,
                                labels=c("COS[1,1]", "COS[2,1]", "COS[3,1]", "COS[4,1]", "COS[5,1]")),
                              umxPath("Fs", to=latentvars[-1], free=FALSE, #values=startloadingsS,
                                labels=c("SIN[1,1]", "SIN[2,1]", "SIN[3,1]", "SIN[4,1]", "SIN[5,1]")),
                              umxPath(var = c("Fc","Fs"), freeAt=.5, labels="beta1"), 
                              mxAlgebra(1-beta1, name="beta0"),   # Constrain beta0 to 1 - beta1
                              umxPath(var = "gamma", labels="beta0[1,1]", free=FALSE),   # Use constraint to define beta0
                              mxAlgebra(Angles * 180/pi, name="Degrees")
                              )

Here, I want to constrain the factor loadings of the variables onto two latent factors to be the sines and cosines of a vector of angles. I can do so by individually listing the matrix elements of the MxAlgebra objects. However, this doesn't scale well--to run this same model with 8 variables versus six, I would need to manually add in matrix location calls. I'd like to automate that. Ideally, I would like to be able to refer to the whole matrix from the MxAlgebra objects and get element-wise matching to the parameters I'm constraining. Is there a way to do that? Or do you have a recommendation for how to re-key the model to get the same effect?

If there is no elegant way to do so currently, I'd like to request either the ability to refer to entire matrices in a "labels" argument or otherwise to be able to assign individual labels to the elements of an mxAlgebra object.

Thanks for any insight!

mhunter's picture
Offline
Joined: 07/31/2009 - 15:26
Use R

Hi!

I think this is where R has an opportunity to shine. I'd replace

umxPath("Fs", to=latentvars[-1], free=FALSE, #values=startloadingsS,
                 labels=c("SIN[1,1]", "SIN[2,1]", "SIN[3,1]", "SIN[4,1]", "SIN[5,1]"))

with

# Set nVar
nVar <- 6 # number of observed variables
 
# Create path label programmatically depending on nVar
umxPath("Fs", to=latentvars[-1], free=FALSE, #values=startloadingsS,
                 labels=paste0('SIN[', 1:nVar, ', 1]'))

Note that the new labels, paste0('SIN[', 1:nVar, ', 1]'), creates a vector of strings with the labels you want: e.g.

> paste0('SIN[', 1:nVar, ', 1]')
[1] "SIN[1, 1]" "SIN[2, 1]" "SIN[3, 1]" "SIN[4, 1]" "SIN[5, 1]" "SIN[6, 1]"
bwiernik's picture
Offline
Joined: 01/30/2014 - 19:39
Ah, nice! paste is the

Ah, nice! paste is the obvious solution. Much appreciated.