Examples of Longitudinal Models with Time-varying Covariates

The saved examples below were generated with nlpsem 1.0.0.9006; extdata/REGENERATED.txt records the versions and how the fits compare with the previous ones. Rendering this guide does not refit its disabled model-fitting chunks. Refit with the current version for a new analysis, use getDiagnostics() to check admissibility and uncertainty, and compare multiple starts for difficult nonlinear or mixture models. These examples are not evidence of numerical qualification.

Load nlpsem package, dependent packages and set CSOLNP as the optimizer

library(nlpsem)
mxOption(model = NULL, key = "Default optimizer", "CSOLNP", reset = FALSE)

Load pre-computed models

load(system.file("extdata", "getTVCmodel_examples.RData", package = "nlpsem"))

Load example data and preprocess data

# Load ECLS-K (2011) data
data("RMS_dat")
RMS_dat0 <- RMS_dat
# Re-baseline the data so that the estimated initial status is for the
# starting point of the study
baseT <- RMS_dat0$T1
RMS_dat0$T1 <- (RMS_dat0$T1 - baseT)/12
RMS_dat0$T2 <- (RMS_dat0$T2 - baseT)/12
RMS_dat0$T3 <- (RMS_dat0$T3 - baseT)/12
RMS_dat0$T4 <- (RMS_dat0$T4 - baseT)/12
RMS_dat0$T5 <- (RMS_dat0$T5 - baseT)/12
RMS_dat0$T6 <- (RMS_dat0$T6 - baseT)/12
RMS_dat0$T7 <- (RMS_dat0$T7 - baseT)/12
RMS_dat0$T8 <- (RMS_dat0$T8 - baseT)/12
RMS_dat0$T9 <- (RMS_dat0$T9 - baseT)/12
# Standardize time-invariant covariates (TICs)
## ex1 is standardized growth TIC in models
RMS_dat0$ex1 <- scale(RMS_dat0$Approach_to_Learning)
# Standardize time-varying covariate (TVC)
BL_mean <- mean(RMS_dat0[, "R1"])
BL_var <- var(RMS_dat0[, "R1"])
RMS_dat0$Rs1 <- (RMS_dat0$R1 - BL_mean)/sqrt(BL_var)
RMS_dat0$Rs2 <- (RMS_dat0$R2 - BL_mean)/sqrt(BL_var)
RMS_dat0$Rs3 <- (RMS_dat0$R3 - BL_mean)/sqrt(BL_var)
RMS_dat0$Rs4 <- (RMS_dat0$R4 - BL_mean)/sqrt(BL_var)
RMS_dat0$Rs5 <- (RMS_dat0$R5 - BL_mean)/sqrt(BL_var)
RMS_dat0$Rs6 <- (RMS_dat0$R6 - BL_mean)/sqrt(BL_var)
RMS_dat0$Rs7 <- (RMS_dat0$R7 - BL_mean)/sqrt(BL_var)
RMS_dat0$Rs8 <- (RMS_dat0$R8 - BL_mean)/sqrt(BL_var)
RMS_dat0$Rs9 <- (RMS_dat0$R9 - BL_mean)/sqrt(BL_var)
xstarts <- mean(baseT)

Example 1: This example includes two models. Model 1 is a full bilinear spline LGCM with a TVC to examine the influence of baseline teacher-reported approach to learning and the development in reading ability on the development of mathematics ability. It also includes a visualization showcasing the growth status of mathematics ability. Model 2 is a full bilinear spline LGCM with a decomposed TVC (interval-specific slopes) to examine the influence of baseline teacher-reported approach to learning and the development in reading ability on the development of mathematics ability. P values and Wald confidence intervals of all parameters are provided. It also includes a visualization showcasing the growth status of mathematics ability.

set.seed(20191029)
Math_TVC_BLS_f <- getTVCmodel(
  dat = RMS_dat0, t_var = "T", y_var = "M", curveFun = "BLS", intrinsic = TRUE,
  records = 1:9, y_model = "LGCM", TVC = "Rs", decompose = 0, growth_TIC = "ex1",
  tries = 10
  )
set.seed(20191029)
Math_TVCslp_BLS_f <- getTVCmodel(
  dat = RMS_dat0, t_var = "T", y_var = "M", curveFun = "BLS", intrinsic = TRUE,
  records = 1:9, y_model = "LGCM", TVC = "Rs", decompose = 1, growth_TIC = "ex1",
  tries = 10, paramOut = TRUE
  )
getEstimateStats(est_in = Math_TVCslp_BLS_f@Estimates, CI_type = "Wald")
#> An object of class "StatsOutput"
#> Slot "wald":
#>                  Estimate          SE p.value wald_lbound wald_ubound
#> Y_alpha0     3.711576e+01 0.405734396 <0.0001 36.32053860 37.91098821
#> Y_alpha1     2.048744e+01 0.206082459 <0.0001 20.08352332 20.89135172
#> Y_alpha2     8.206438e+00 0.187798110 <0.0001  7.83836011  8.57451517
#> Y_alphag     3.159997e+00 0.041813848 <0.0001  3.07804299  3.24195026
#> Y_psi00      4.721345e+01 4.186383190 <0.0001 39.00829208 55.41861264
#> Y_psi01     -1.205055e+00 1.631979064  0.4603 -4.40367489  1.99356548
#> Y_psi02     -2.294568e+00 1.498461631  0.1257 -5.23149905  0.64236261
#> Y_psi0g     -3.718480e-01 0.304193140  0.2216 -0.96805563  0.22435956
#> Y_psi11      1.216684e+01 1.192823576 <0.0001  9.82895176 14.50473426
#> Y_psi12     -2.186928e-01 0.794360759  0.7831 -1.77561130  1.33822565
#> Y_psi1g     -7.959253e-01 0.187914599 <0.0001 -1.16423117 -0.42761948
#> Y_psi22      3.325021e+00 1.144545784  0.0037  1.08175268  5.56828971
#> Y_psi2g     -3.249415e-01 0.178603121  0.0689 -0.67499723  0.02511414
#> Y_psigg      2.938684e-01 0.047995848 <0.0001  0.19979823  0.38793850
#> Y_residuals  2.839216e+01 0.804230430 <0.0001 26.81589599 29.96842135
#> X_mueta0     9.309360e-03 0.055610685  0.8671 -0.09968558  0.11830430
#> X_mueta1     2.503646e+00 0.070159205 <0.0001  2.36613620  2.64115523
#> X_psi00      1.212426e+00 0.085609223 <0.0001  1.04463496  1.38021695
#> X_psi01     -7.761133e-02 0.020249778   1e-04 -0.11730016 -0.03792249
#> X_psi11      9.802161e-02 0.010636629 <0.0001  0.07717420  0.11886902
#> X_rel_rate2  6.947270e-01 0.038405283 <0.0001  0.61945403  0.76999997
#> X_rel_rate3  1.247841e+00 0.043115852 <0.0001  1.16333573  1.33234676
#> X_rel_rate4  4.902895e-01 0.030289016 <0.0001  0.43092413  0.54965489
#> X_rel_rate5  7.110086e-01 0.033019516 <0.0001  0.64629151  0.77572563
#> X_rel_rate6  2.823416e-01 0.016859708 <0.0001  0.24929718  0.31538602
#> X_rel_rate7  3.019077e-01 0.016795010 <0.0001  0.26899009  0.33482532
#> X_rel_rate8  2.567693e-01 0.016476220 <0.0001  0.22447647  0.28906206
#> X_abs_rate2  2.503646e+00 0.070159205 <0.0001  2.36613620  2.64115523
#> X_abs_rate3  1.739350e+00 0.066353262 <0.0001  1.60930027  1.86940028
#> X_abs_rate4  3.124152e+00 0.066374286 <0.0001  2.99406118  3.25424360
#> X_abs_rate5  1.227511e+00 0.067973481 <0.0001  1.09428567  1.36073681
#> X_abs_rate6  1.780114e+00 0.065622020 <0.0001  1.65149677  1.90873036
#> X_abs_rate7  7.068833e-01 0.038030439 <0.0001  0.63234505  0.78142163
#> X_abs_rate8  7.558699e-01 0.036725756 <0.0001  0.68388877  0.82785109
#> X_abs_rate9  6.428593e-01 0.037530518 <0.0001  0.56930081  0.71641774
#> X_residuals  3.586983e-01 0.008794175 <0.0001  0.34146200  0.37593454
#> betaTIC0     9.664645e-01 0.388817293  0.0129  0.20439660  1.72853238
#> betaTIC1     1.190497e-01 0.208122507  0.5673 -0.28886288  0.52696236
#> betaTIC2    -2.104573e-01 0.193819237  0.2775 -0.59033600  0.16942145
#> betaTICg     4.942311e-03 0.039089345  0.8994 -0.07167140  0.08155602
#> betaTVC0     7.623010e+00 0.379391383 <0.0001  6.87941649  8.36660338
#> betaTVC1     8.497488e-01 0.201782976 <0.0001  0.45426145  1.24523618
#> betaTVC2    -3.466522e-01 0.189955874   0.068 -0.71895886  0.02565449
#> betaTVCg    -1.271951e-01 0.039057191  0.0011 -0.20374575 -0.05064437
#> muTIC        5.570162e-07 0.044669625 >0.9999 -0.08755030  0.08755141
#> phiTIC       9.980007e-01 0.063132216 <0.0001  0.87426383  1.12173756
#> Y_mueta0     3.718673e+01 0.545018363 <0.0001 36.11851293 38.25494565
#> Y_mueta1     2.049535e+01 0.206120882 <0.0001 20.09135870 20.89933771
#> Y_mueta2     8.203210e+00 0.188906209 <0.0001  7.83296105  8.57345978
#> Y_mu_knot    3.158813e+00 0.041757326 <0.0001  3.07696967  3.24065538
#> covBL        4.000059e-01 0.052300670 <0.0001  0.29749847  0.50251333
#> kappa        1.778886e+00 0.105950460 <0.0001  1.57122660  1.98654477
#> Cov_XYres    5.509761e-01 0.061897925 <0.0001  0.42965842  0.67229382
#> 
#> Slot "likelihood":
#> data frame with 0 columns and 0 rows
#> 
#> Slot "bootstrap":
#> data frame with 0 columns and 0 rows
Figure1 <- getFigure(
  model = Math_TVC_BLS_f@mxOutput, sub_Model = "TVC", y_var = "M", curveFun = "BLS", 
  y_model = "LGCM", t_var = "T", records = 1:9, xstarts = xstarts, xlab = "Year",
  outcome = "Mathematics"
)
show(Figure1)
#> figOutput Object
#> --------------------
#> Trajectories: 1 
#> Figure 1:
#> `geom_smooth()` using method = 'gam' and formula = 'y ~ s(x, bs = "cs")'

Mathematics mean trajectory over years from a random-knot bilinear spline growth model with a direct time-varying covariate, comparing the fitted mean and smoothed observed mean with pointwise 95 percent confidence limits.

Figure2 <- getFigure(
  model = Math_TVCslp_BLS_f@mxOutput, sub_Model = "TVC", y_var = "M", curveFun = "BLS", 
  y_model = "LGCM", t_var = "T", records = 1:9, xstarts = xstarts, xlab = "Year",
  outcome = "Mathematics"
)
show(Figure2)
#> figOutput Object
#> --------------------
#> Trajectories: 1 
#> Figure 1:
#> `geom_smooth()` using method = 'gam' and formula = 'y ~ s(x, bs = "cs")'

Mathematics mean trajectory over years from a random-knot bilinear spline growth model with interval-slope covariate decomposition, comparing the fitted mean and smoothed observed mean with pointwise 95 percent confidence limits.

Figures 1 and 2 show each model’s growth component, which leaves out the TVC effect; the dashed line adds it back. With the TVC entered directly, the growth component leaves out the TVC’s full value at each occasion, while with interval-specific slopes it leaves out only the slope effect, so the two components describe different quantities.

The saved Model 1 is a local optimum of a likelihood with several: its -2LL is 47324.02, while the same model reaches 47225.92 when time is measured in months instead of years. Compare the solutions from several starts before interpreting a random-knot model.

Example 2: Fit reduced bilinear spline LGCMs with a decomposed TVC (interval-specific slopes, interval-specific changes, and change from baseline) to examine the influence of baseline teacher-reported approach to learning and the development in reading ability on the development of mathematics ability. It also includes a visualization showcasing the growth status of mathematics ability.

set.seed(20191029)
Math_TVCslp_BLS_r <- getTVCmodel(
  dat = RMS_dat0, t_var = "T", y_var = "M", curveFun = "BLS", intrinsic = FALSE,
  records = 1:9, y_model = "LGCM", TVC = "R", decompose = 1, growth_TIC = "ex1",
  tries = 10, paramOut = TRUE)
set.seed(20191029)
Math_TVCchg_BLS_r <- getTVCmodel(
  dat = RMS_dat0, t_var = "T", y_var = "M", curveFun = "BLS", intrinsic = FALSE,
  records = 1:9, y_model = "LGCM", TVC = "R", decompose = 2, growth_TIC = "ex1",
  tries = 10, paramOut = TRUE)
set.seed(20191029)
Math_TVCchgBL_BLS_r <- getTVCmodel(
  dat = RMS_dat0, t_var = "T", y_var = "M", curveFun = "BLS", intrinsic = FALSE,
  records = 1:9, y_model = "LGCM", TVC = "R", decompose = 3, growth_TIC = "ex1",
  tries = 10, paramOut = TRUE)    
Figure3 <- getFigure(
  model = Math_TVCslp_BLS_r@mxOutput, sub_Model = "TVC", y_var = "M", curveFun = "BLS", 
  y_model = "LGCM", t_var = "T", records = 1:9, xstarts = xstarts, xlab = "Year",
  outcome = "Mathematics"
)
show(Figure3)
#> figOutput Object
#> --------------------
#> Trajectories: 1 
#> Figure 1:
#> `geom_smooth()` using method = 'gam' and formula = 'y ~ s(x, bs = "cs")'

Mathematics mean trajectory over years from a fixed-knot bilinear spline growth model with interval-slope covariate decomposition, comparing the fitted mean and smoothed observed mean with pointwise 95 percent confidence limits.

Figure4 <- getFigure(
  model = Math_TVCchg_BLS_r@mxOutput, sub_Model = "TVC", y_var = "M", curveFun = "BLS", 
  y_model = "LGCM", t_var = "T", records = 1:9, xstarts = xstarts, xlab = "Year",
  outcome = "Mathematics"
)
show(Figure4)
#> figOutput Object
#> --------------------
#> Trajectories: 1 
#> Figure 1:
#> `geom_smooth()` using method = 'gam' and formula = 'y ~ s(x, bs = "cs")'

Mathematics mean trajectory over years from a fixed-knot bilinear spline growth model with interval-change covariate decomposition, comparing the fitted mean and smoothed observed mean with pointwise 95 percent confidence limits.

Figure5 <- getFigure(
  model = Math_TVCchgBL_BLS_r@mxOutput, sub_Model = "TVC", y_var = "M", curveFun = "BLS", 
  y_model = "LGCM", t_var = "T", records = 1:9, xstarts = xstarts, xlab = "Year",
  outcome = "Mathematics"
)
show(Figure5)
#> figOutput Object
#> --------------------
#> Trajectories: 1 
#> Figure 1:
#> `geom_smooth()` using method = 'gam' and formula = 'y ~ s(x, bs = "cs")'

Mathematics mean trajectory over years from a fixed-knot bilinear spline growth model with change-from-baseline covariate decomposition, comparing the fitted mean and smoothed observed mean with pointwise 95 percent confidence limits.

Check the change-from-baseline example

The saved Math_TVCchgBL_BLS_r example reaches optimizer status 0, and getDiagnostics() reports no issues:

getDiagnostics(Math_TVCchgBL_BLS_r)$issues
#> character(0)

An earlier fit of the same call (nlpsem 1.0.0.9000) also reached status 0, at a poorer optimum (-2LL 64317.60 against 64207.48) with a negative latent residual variance (Y_psi22, about -1.40): optimizer status alone does not distinguish such solutions.