# principles and practice of sem, 5th ed.
# rex b. kline, guilford press, 2023
# chapter 16, table 16.2, analysis 2
# zero error variance model and partially reduced
# form model for SES only
# to avoid the problem that some R packages share the same name
# for different functions, all functions are specified next as
# package::function
# which prevents masking, or the default hiding of
# a function with a redundant name from a package used next
date()
v <- R.Version()
print(paste0(v$language, " version ", v$major, ".",
v$minor, " (", v$year, "-", v$month, "-", v$day, ")"))
library(lavaan)
# get citation information
citation("lavaan", auto = TRUE)
# input the correlations in lower diagnonal form
shenLower.cor <- '
1.00
.44 1.00
.69 .54 1.00
.21 .08 .16 1.00
.23 .15 .19 .19 1.00
.12 .08 .08 .08 -.03 1.00
.09 .06 .04 .01 -.02 .38 1.00
.03 .02 -.02 -.07 -.11 .37 .46 1.00 '
# name the variables and convert to full correlation matrix
shen.cor <- lavaan::getCov(shenLower.cor, names = c("acculscl", "status",
"percent", "educ", "income", "interpers", "job", "scl90d"))
# add the standard deviations and convert to covariances
shen.cov <- cor2cov(shen.cor, sds = c(3.60,3.30,2.45,3.27,3.44,2.99,
3.58,3.70))
options(width = 130)
# display correlations and covariances
shen.cor
shen.cov
# scl90d score reliability (alpha) is .90 from
# derogatis et al. (1976)
# sample variance is 3.70**2 = 13.690
# error variance fixed to (1 - .90) * 13.690 = 1.369
# define fit statistics for later comparison display
fit.stats1 <- c("chisq", "df", "pvalue", "cfi", "srmr")
fit.stats2 <- c("rmsea", "rmsea.ci.lower", "rmsea.ci.upper")
# specify figure 16.2(b)
# zero error variance model
# ses with composite indicators (educ, income)
# educ, income each covary with acculturation factor
# special lavaan syntax for composite indicators
# "<~" defines a composite where the disturbance
# variance is automatically fixed to zero
# composite is explicitly scaled with an ULI constraint
shenSEScomposite.model <- '
# ses composite
SES <~ 1*educ + income
# reflective factors
Acculturation =~ acculscl + status + percent
status ~~ percent
Stress =~ interpers + job
Depression =~ scl90d
scl90d ~~ 1.369*scl90d
# covariances among exogenous acculturation factor
# and composite indicators of ses explicitly defined
# as free parameters
Acculturation ~~ income + educ
income ~~ educ
# covariance between ses composite and acculturation
# factor fixed to zero
Acculturation ~~ 0*SES
# structural model
Stress ~ Acculturation
# depression regressed on ses composite and
# reflective stress factor
# coefficient for SES labeled for calculation of
# indirect effects through the SES composite
Depression ~ b*SES + Stress '
# specify figure 16.2(c)
# partially reduced form model with
# no SES composite
shenSESnoComposite.model <- '
# reflective factors
Acculturation =~ acculscl + status + percent
status ~~ percent
Stress =~ interpers + job
Depression =~ scl90d
scl90d ~~ 1.369*scl90d
# covariances among exogenous acculturation factor
# and the measured exogenous variables income and education
# explicitly declared as free parameters
Acculturation ~~ income + educ
income ~~ educ
# structural model
Stress ~ Acculturation
# depression regressed on income, educ, and
# reflective stress factor
Depression ~ educ + income + Stress '
# fit figure 16.2(b) to data
shenSEScomposite <- lavaan::sem(shenSEScomposite.model, sample.cov = shen.cov,
sample.nobs = 983, fixed.x=FALSE)
# fit figure 16.2(c) to data
shenSESnoComposite <- lavaan::sem(shenSESnoComposite.model, sample.cov = shen.cov,
sample.nobs=983, fixed.x = FALSE)
# list values of global fit statistics
# for both models, which are equivalent
# figure 16.2(b)
lavaan::fitMeasures(shenSEScomposite, fit.stats1)
lavaan::fitMeasures(shenSEScomposite, fit.stats2)
# figure 16.2(c)
lavaan::fitMeasures(shenSESnoComposite, fit.stats1)
lavaan::fitMeasures(shenSESnoComposite, fit.stats2)
# residuals for both models, which are
# also equal
# figure 16.2(b)
lavaan::residuals(shenSEScomposite, type = "raw")
lavaan::residuals(shenSEScomposite, type = "standardized.mplus")
lavaan::residuals(shenSEScomposite, type = "cor.bollen")
# figure 16.2(c)
lavaan::residuals(shenSESnoComposite, type = "raw")
lavaan::residuals(shenSESnoComposite, type = "standardized.mplus")
lavaan::residuals(shenSESnoComposite, type = "cor.bollen")
# parameter estimates and residuals
# figure 16.2(b)
lavaan::summary(shenSEScomposite, header = FALSE, fit.measures = FALSE,
standardized = TRUE, rsquare = TRUE)
# figure 16.2(c)
lavaan::summary(shenSESnoComposite, header = FALSE, fit.measures = FALSE,
standardized = TRUE, rsquare = TRUE)