This is the multi-level (two-level) analogue of the varcov family: it models the within-cluster and between-cluster variance-covariance matrices of clustered data directly, without a latent-variable layer. Each level can be parameterized independently through the within and between arguments: "cov" models a covariance matrix directly, "chol" a Cholesky decomposition, "prec" a precision matrix, "ggm" a Gaussian graphical model (the multi-level GGM; alias ml_ggm() sets both levels to "ggm") and "cor" a correlation matrix (alias ml_corr() sets both levels to "cor").
Two estimators are supported, exactly as in ml_lvm: "ML", the two-level sufficient-statistics Gaussian maximum-likelihood estimator (its computational cost does not depend on the number of units per cluster), and "FIML", wide-format full-information maximum likelihood (the natural choice with missing data). Both maximize the same likelihood and give identical estimates on complete data. The default picks "ML" for complete data with more than five units per cluster and "FIML" otherwise.
The multi-level GGM (ml_ggm) is also implemented, using a different (nodewise multilevel regression) estimator, in the mlGGM function of the mlVAR package. The psychonetrics implementation here estimates the full two-level covariance structure by maximum likelihood instead.
This framework is experimental (a message is shown once per session).
ml_varcov(data, clusters, vars,
within = c("cov", "chol", "prec", "ggm", "cor"),
between = c("cov", "chol", "prec", "ggm", "cor"),
groups, groupvar,
sigma_within = "full", lowertri_within = "full",
omega_within = "full", delta_within = "diag",
kappa_within = "full", rho_within = "full", SD_within = "full",
sigma_between = "full", lowertri_between = "full",
omega_between = "full", delta_between = "diag",
kappa_between = "full", rho_between = "full", SD_between = "full",
mu, equal = "none", baseline_saturated = TRUE,
estimator = c("default", "ML", "FIML"),
optimizer, storedata = FALSE,
standardize = c("none", "z", "quantile"), sampleStats,
verbose = FALSE)ml_ggm(...)
ml_corr(...)
An object of the class psychonetrics (psychonetrics-class).
A data frame in long format: one row per unit, with a column identifying the cluster each unit belongs to.
String indicating the name of the cluster (grouping) variable in data. May not be missing.
Character vector of the variables to include. If missing, all columns except clusters and the grouping variable are used.
The parameterization of the within-cluster covariance matrix. One of "cov", "chol", "prec", "ggm" or "cor".
The parameterization of the between-cluster covariance matrix. One of "cov", "chol", "prec", "ggm" or "cor".
Deprecated alias for groupvar.
An optional string indicating the name of a variable for a multi-group analysis.
Only used when within = "cov". Either "full", "diag" or a matrix specifying the covariance structure of the within block (0 = fixed to 0, 1 = free, higher integers = equality constraints).
Only used when within = "chol". As sigma_within, for the lower-triangular Cholesky factor.
Only used when within = "ggm". As sigma_within, for the within partial-correlation network (only the off-diagonal is used).
Only used when within = "ggm". As sigma_within, for the within diagonal scaling matrix.
Only used when within = "prec". As sigma_within, for the within precision matrix.
Only used when within = "cor". As sigma_within, for the within correlation matrix.
Only used when within = "cor". As sigma_within, for the within standard-deviation scaling matrix.
As sigma_within, for the between-cluster block (used when between = "cov").
As lowertri_within, for the between-cluster block.
As omega_within, for the between-cluster block.
As delta_within, for the between-cluster block.
As kappa_within, for the between-cluster block.
As rho_within, for the between-cluster block.
As SD_within, for the between-cluster block.
Optional vector encoding the mean structure. Set elements to 0 to indicate fixed zeroes.
A character vector indicating which matrices should be constrained equal across groups.
A logical indicating whether the baseline and saturated models should be included. Mostly used internally and should be kept to TRUE.
"ML" (two-level sufficient-statistics ML), "FIML" (wide-format full-information ML) or "default" ("ML" for complete data with more than five units per cluster, "FIML" otherwise). The estimator is fixed at model creation and cannot be switched afterwards. Note that the EBIC fit measures under "FIML" inherit the wide-format variable count from the sample statistics (as in ml_lvm), whereas under "ML" they use the number of modelled variables.
The optimizer to be used. Usually left missing to use the default.
Logical, should the raw data be stored? Needed for bootstrapping.
Optional grand standardization of the raw variables before estimation: "none", "z" (z-scores) or "quantile".
An optional sample statistics object. Mostly used internally.
Logical, should progress be printed to the console?
Arguments passed to ml_varcov by ml_ggm and ml_corr.
Sacha Epskamp <mail@sachaepskamp.com>
For unit \(j\) in cluster \(i\) the observed response is decomposed into a within-cluster and a between-cluster component,
$$y_{ij} = \mu + \eta^{(W)}_{ij} + \eta^{(B)}_{i},$$
with \(\eta^{(W)}_{ij} \sim N(0, \Sigma_W)\) and \(\eta^{(B)}_{i} \sim N(0, \Sigma_B)\) independent, so that \(\mathrm{var}(y_{ij}) = \Sigma_W + \Sigma_B\) and \(\mathrm{cov}(y_{ij}, y_{ij'}) = \Sigma_B\) for two units in the same cluster. \(\Sigma_W\) (sigma_within) and \(\Sigma_B\) (sigma_between) are each parameterized according to the within and between arguments; for the "ggm" parameterization \(\Sigma = \Delta (I - \Omega)^{-1} \Delta\) with partial-correlation network \(\Omega\) (omega_within / omega_between) and scaling \(\Delta\) (delta_within / delta_between).
This is the special case of ml_lvm in which the loadings matrix equals the identity and there is no residual variance, but it is implemented as its own framework with its own matrix names (sigma_within, omega_within, sigma_between, omega_between, ...) and its own (simpler) analytic derivatives.
Epskamp, S., Rhemtulla, M., & Borsboom, D. (2017). Generalized network psychometrics: Combining network and latent variable models. Psychometrika, 82(4), 904-927. tools:::Rd_expr_doi("10.1007/s11336-017-9557-x")
Hamaker, E. L., & Muthen, B. (2020). The fixed versus random effects debate and how it relates to centering in multilevel modeling. Psychological Methods, 25(3), 365-379.
McDonald, R. P., & Goldstein, H. (1989). Balanced versus unbalanced designs for linear structural relations in two-level data. British Journal of Mathematical and Statistical Psychology, 42(2), 215-232.
varcov for the single-level variance-covariance family, ggm for the single-level GGM, and ml_lvm for the multi-level latent variable model that supplies the estimator.
if (FALSE) {
library("dplyr")
# Simulate two-level data (200 clusters of 8 units, 4 variables):
set.seed(1)
nCluster <- 200; perCluster <- 8; p <- 4
cl <- rep(seq_len(nCluster), each = perCluster)
# True within and between covariance matrices:
SigmaW <- diag(p); SigmaW[1,2] <- SigmaW[2,1] <- 0.4
SigmaB <- diag(0.5, p); SigmaB[3,4] <- SigmaB[4,3] <- 0.2
b <- MASS::mvrnorm(nCluster, rep(0, p), SigmaB)
Y <- b[cl, ] + MASS::mvrnorm(nCluster * perCluster, rep(0, p), SigmaW)
Data <- as.data.frame(Y)
names(Data) <- paste0("V", 1:p)
Data$cluster <- cl
# Fit a multi-level GGM (both levels a Gaussian graphical model):
mod <- ml_ggm(Data, vars = paste0("V", 1:p), clusters = "cluster")
mod <- mod %>% runmodel
# Inspect the estimated within- and between-cluster networks:
getmatrix(mod, "omega_within")
getmatrix(mod, "omega_between")
# Prune non-significant edges and re-fit:
mod <- mod %>% prune(alpha = 0.05)
}
Run the code above in your browser using DataLab