pirt: Projective IRT (PIRT) models

View source: R/pirt.R

pirtR Documentation

Projective IRT (PIRT) models

Description

Computes the projective IRT model parameters either using the logistic kernel approximation approaches (Stucky et al. 2013; Ip 2010/Doebler and Doebler, 2022) or the MML-PIRT approach by Chalmers et al. (in review). These return information pertaining to a lower-dimensional (often unidimensional) IRT model that has marginalized one or more latent traits. When the method is the MML-PIRT a working mirt object will be returned, otherwise if the target is the logistic kernel approximations then a list of the PIRT estimates (and potentially their delta-method SEs) are returned.

Usage

pirt(
  mod,
  model = 1,
  project = 1,
  itemtype = extract.mirt(mod, "itemtype"),
  SE = TRUE,
  estimator = "MML",
  invariance = "",
  IRTpars = FALSE,
  shortform = NULL,
  ...
)

Arguments

mod

fitted model from mirt

model

type of PIRT model to fit to marginalized table

project

which dimension to project to in the stored E-table. Default projects all dimensions to the first dimension (project = 1), as this is the assumed primary dimension in, for instance, bfactor()

itemtype

type of model to fit to the projected marginalized factor. Defaults to the same type as the parent object mod. See mirt for details

SE

logical; compute the ACOV matrix to obtain standard errors (SE)?

estimator

type of PIRT estimator to use. Default is 'MML' to fit and return the MML-PIRT variable described by Chalmers et al. (in review). 'FA' will use Stucky et al.'s (2012) factor analysis logistic approximation to project to the first dimension, and 'LKA' will use the use logistic kernel approximation formula presented in Ip (2010)/Doebler and Doebler(2020), however these only project to the first dimension? The latter two estimators are also only applicable when input model is from the M*PL and MGRM family (see for polytomous MGRM derivation), and only return lists of the resulting parameters and SE estimates

Note that for methods other than 'MML' the SEs will be returned only if the parent model as a suitably estimated ACOV matrix to perform the delta method (e.g., bfactor(..., SE=TRUE)

invariance

type of group invariance to specify (see multipleGroup). Included here as the multiple-group PIRT approach needs to also calibrate the scale and location of the reference group, which is done silently internally whenever 'free_means' or 'free_vars' are specified

IRTpars

logical; report classical IRT parameterization and SEs? Only used when FAapprox = TRUE

shortform

character vector of item names, or numeric vector of item locations, used create a short-form by specifying which items to extract from the PIRT model. For instance, selecting one item from each specific factor has the property of identical marginal and conditional bifactors (see Stucky, Thissen, and Elden, 2013). Only supported when using the MML-PIRT approach as this returns the associated model object

...

extra information passed to the estimation engine

Details

Logistic kernel approximation approaches are limited only to the M2PL (and related models, like the M4PL) and MGRM family of ordinal models, while MML-PIRT can be applied to any MIRT model supported by the package.

Standard error are computed when FAapprox = TRUE via the delta method only when the parent model estimated the ACOV matrix, while the MML-PIRT approach does not require this prerequisite as the ACOV can be computed directly. By default, MML-PIRT computes the associated ACOV matrix using the Oakes' identity given then marginalized E-table.

References

Chalmers, R. P., Falk, C. F., Reise, S. P. (in review). A General Approach for Estimating Projective IRT Models. Applied Psychological Measurement.

Doebler, A., and Doebler, P. (2022). Rotate and Project: Measurement of the Intended Concept with Unidimensional Item Response Theory. from Multidimensional Ordinal Items. Multivariate Behavioral Research, 57 (1), 40-56.

Ip, H. (2010). Empirically indistinguishable multidimensional IRT and locally dependent unidimensional item response models. British Journal of Mathematical and Statistical Psychology, 63(2),395-416.

Stucky, B. D., Thissen, D., & Orlando E., M. (2012). Using Logistic Approximations of Marginal Trace Lines to Develop Short Assessments. Applied Psychological Measurement, 37(1), 41-57.

Examples




# Table 3 in Ip (2010)
as <- cbind(rep(c(2.63, 1.63, 1.38), each=5),
            c(rep(3.07, 5), numeric(10)),
            c(numeric(5), rep(1.36, 5), numeric(5)),
            c(numeric(10), rep(.69,5)))
as

set.seed(8675309)
d <- round(rnorm(15, 0, sd=1.5), 2)
nitems <- length(d)
nfact <- ncol(as)
dat <- simdata(as, d, 10000, itemtype='2PL')
itemstats(dat)


# bifactor model, storing E-table
mod <- bfactor(dat,
               "S1 = 1-5
                S2 = 6-10
                S3 = 11-15")
summary(mod)
coef(mod, simplify=TRUE)$items

# PIRT model via MML-PIRT
pmod <- pirt(mod)
coef(pmod)
coef(pmod, printSE=TRUE)
coef(pmod, simplify=TRUE)$items

# Logistic approximations (parameters only)
pirt(mod, estimator = 'FA')
pirt(mod, estimator = 'LKA')  # effectively the same

# plots
plot(pmod)
plot(pmod, type = 'info')
plot(pmod, type = 'itemscore')
plot(pmod, type = 'infotrace')
itemplot(pmod, 1, type = 'info', CE=TRUE)

# standardized loadings
summary(pmod)

# factor scores (EAP). Not optimal as the estimates/SEs ignore
#   the marginal components
fscores(pmod, method = 'EAPsum', full.scores=FALSE) # EAPs for sum-scores

# EAPs using Lord-Wingersky 2.0 approach (recommended if using sum-scores)
fscores(mod, method = 'EAPsum_2.0', full.scores=FALSE)

# EAP scores from full response data (not generally recommended)
fscores(pmod, full.scores=FALSE) |> head()
fs <- fscores(pmod)

# compare to bifactor scores (marginal vs conditional)
bfs <- fscores(mod, method = 'MAP')
cor(bfs[,1], fs)

# item fit (silly, but possible)
itemfit(pmod)

# three item shortform by taking the highest PIRT discrimination/slope terms
# per specific factor to ensure that the marginal and joint likelihood
# functions are comparable (see Stucky et al. 2013 for details)
slopes <- coef(pmod, simplify=TRUE)$items[,'a1']
slopes
namemax <- \(slp) names(slp)[which.max(slp)]
shortform <- c(namemax(slopes[1:5]),
               namemax(slopes[6:10]), namemax(slopes[11:15]))
pirt_short <- pirt(mod, shortform=shortform)
coef(pirt_short, simplify=TRUE)$items

# EAP-sum for short form
fscores(pirt_short, method='EAPsum', full.scores=FALSE)

###########################
# same example, but with polytomous data

# Table 3 in Ip (2010)
as <- cbind(rep(c(2.63, 1.63, 1.38), each=5),
            c(rep(3.07, 5), numeric(10)),
            c(numeric(5), rep(1.36, 5), numeric(5)),
            c(numeric(10), rep(.69,5)))
as

set.seed(8675309)
diffs <- t(apply(matrix(runif(20*4, .5, 1), 20), 1, cumsum))
diffs <- -(diffs - rowMeans(diffs))
d <- diffs + rnorm(20)
nitems <- nrow(d)
nfact <- ncol(as)
dat <- simdata(as, d, 10000, itemtype='graded')
itemstats(dat)

# bifactor model, storing E-table
mod <- bfactor(dat,
               "S1 = 1-5
                S2 = 6-10
                S3 = 11-15")
summary(mod)
coef(mod, simplify=TRUE)$items

# PIRT model via MML-PIRT
pmod <- pirt(mod)
coef(pmod)
coef(pmod, printSE=TRUE)
coef(pmod, simplify=TRUE)$items

# Logistic approximations (parameters only)
pirt(mod, estimator = 'FA')
pirt(mod, estimator = 'LKA')  # see Doebler and Doebler (2020)

# plots
plot(pmod)
plot(pmod, type = 'info')
plot(pmod, type = 'trace')
plot(pmod, type = 'infotrace')
itemplot(pmod, 1, type = 'info', CE=TRUE)

# standardized loadings
summary(pmod)

# factor scores (EAP)
fscores(pmod, method = 'EAPsum', full.scores=FALSE) # EAPs for sum-scores

# EAP scores from full response data
fs <- fscores(pmod)

# compare to bifactor scores (marginal vs conditional)
bfs <- fscores(mod, method = 'MAP')
cor(bfs[,1], fs)


###########################
# Two tier example projected to simple structure

# simulate data
set.seed(1234)
a <- matrix(c(
    0,1,0.5,NA,NA,
    0,1,0.5,NA,NA,
    0,1,0.5,NA,NA,
    0,1,0.5,NA,NA,
    0,1,0.5,NA,NA,
    0,1,NA,0.5,NA,
    0,1,NA,0.5,NA,
    0,1,NA,0.5,NA,
    1,0,NA,0.5,NA,
    1,0,NA,0.5,NA,
    1,0,NA,0.5,NA,
    1,0,NA,NA,0.5,
    1,0,NA,NA,0.5,
    1,0,NA,NA,0.5,
    1,0,NA,NA,0.5,
    1,0,NA,NA,0.5),ncol=5,byrow=TRUE)

d <- matrix(rnorm(16))
items <- rep('2PL', 16)

sigma <- diag(5)
sigma[1,2] <- sigma[2,1] <- .4
dataset <- simdata(a,d,2000,itemtype=items,sigma=sigma)
itemstats(dataset)

specific <- "
S1 = 1-5
S2 = 6-11
S3 = 12-16"

model <- '
    G1 = 1-8
    G2 = 9-16
    COV = G1*G2'

# quadpts dropped for faster estimation, but not as precise
simmod <- bfactor(dataset, specific, model, quadpts = 15, TOL = 1e-3)
coef(simmod, simplify=TRUE)

# simple structure projection
pirt2 <- pirt(simmod, model=model, project=1:2)
coef(pirt2, simplify=TRUE)




mirt documentation built on Aug. 22, 2026, 9:07 a.m.