yrosseel / lavaan

an R package for structural equation modeling and more
http://lavaan.org
412 stars 99 forks source link

Problem with mixing parameter labels and constraints #84

Closed michaelhallquist closed 6 years ago

michaelhallquist commented 6 years ago

Hi Yves,

I would like to identify a multiple-groups measurement invariance model (e.g., weak) using the 'unit variance identification' approach (aka standardized factors). In the multiple-groups case, all loadings are free parameters that are equated between groups. The factor variances are fixed to 1 in one group, but free in the others. I tried to specify this using a parameter vector that contains a 1 for one group, but a label for the other. This led lavaan to apply the label to both groups as an equality constraint. Syntax follows:

#trying to mix constraints and labels to achieve ULI in two groups
mmod_uvi <-'
  visual  =~ NA*x1 + x2 + x3
  textual =~ NA*x4 + x5 + x6
  speed   =~ NA*x7 + x8 + x9 

#does not work -- applies an equality constraint
visual ~~ c(1, v2)*visual
textual ~~ c(1, t2)*textual
speed ~~ c(1, s3)*speed
'

mweak_uvi_bad <- sem(mmod_uvi, data = HolzingerSwineford1939, std.lv=FALSE, group = "school", group.equal="loadings", meanstructure=TRUE)

Thanks for continuing to develop this excellent package! Michael

michaelhallquist commented 6 years ago

I forgot to mention that one way around the above is to label both parameters, but then set one group to 1.0 using a constraint. This works, but is a bit clunky and the odd side effects of the above problems (unexpected equality constraint) made me think it was worth reporting as a bug.

Here's the variant that works currently:

#use constraint to achieve the variance = 1 constraint
mmod_uvi <-'
  visual  =~ NA*x1 + x2 + x3
  textual =~ NA*x4 + x5 + x6
  speed   =~ NA*x7 + x8 + x9 

#label both
visual ~~ c(v1, v2)*visual
textual ~~ c(t1, t2)*textual
speed ~~ c(s1, s3)*speed

#use constraints to enforce structure
v1==1
t1==1
s1==1
'

mweak_uvi_good <- sem(mmod_uvi, data = HolzingerSwineford1939, std.lv=FALSE, group = "school", group.equal="loadings", meanstructure=TRUE)

Michael

yrosseel commented 6 years ago

Thanks Michael for the report. This is not a 'bug' per se, but more something that is not implemented (yet?). You can not mix labels and constants. But you can write:

visual ~~ c(v1, v2)visual + c(1,NA)visual

So you can have the same lhs element multiple times, each one with its own set of modifiers. Here, the first one adds the labels, while the second one handles the constants.

michaelhallquist commented 6 years ago

Ah, thanks, I hadn't considered using different modifiers in separate terms! I'll use that for the time being. If you point me to the parser that determines the role of a given vector, I might be able to create a pull request that does checks on the terms to potentially allow mixing.