| Title: | Heteroscedasticity Diagnostics for Linear Models |
|---|---|
| Description: | Provides a unified set of heteroscedasticity diagnostics for linear-model workflows. It implements classical auxiliary-regression tests, including those of White (1980) <doi:10.2307/1912934>, Breusch and Pagan (1979) <doi:10.2307/1911963>, Koenker (1981) <doi:10.1016/0304-4076(81)90062-2>, Goldfeld and Quandt (1965) <doi:10.1080/01621459.1965.10480811> and Harvey (1976) <doi:10.2307/1913974>; the score test of Cook and Weisberg (1983) <doi:10.1093/biomet/70.1.1>; the ARCH test of Engle (1982) <doi:10.2307/1912773>; and group-wise tests of equal variance, including those of Bartlett (1937) <doi:10.1098/rspa.1937.0109>, Brown and Forsythe (1974) <doi:10.1080/01621459.1974.10482955> and Hartley (1950) <doi:10.2307/2332383>. Resampling and scalable variants, simulation utilities, diagnostic visualisation and remediation helpers share a consistent interface designed for reproducible statistical workflows and integration with common modelling tools. |
| Authors: | Diogo Ribeiro [aut, cre] (ORCID: <https://orcid.org/0009-0001-2022-7072>) |
| Maintainer: | Diogo Ribeiro <[email protected]> |
| License: | Apache License (>= 2.0) |
| Version: | 0.12.0 |
| Built: | 2026-10-12 23:12:35 UTC |
| Source: | https://github.com/diogoribeiro7/heterotests |
Maintains a registry of diagnostic functions that can be called by
runHeteroTests() and runDiagnostics(). Users can register
custom diagnostics via registerDiagnostic().
.diagnostic_registry.diagnostic_registry
An object of class environment of length 16.
These functions extend the package with more specialized tests for heteroscedasticity such as a studentized Breusch-Pagan test, a bootstrap version of White's test and the Szroeter ordered test.
Fits a GAM using mgcv and compares its residuals to the input linear model.
analyzeMLResiduals(model, data = NULL)analyzeMLResiduals(model, data = NULL)
model |
A fitted |
data |
Data frame used if |
A list with the GAM model, residuals and RMSE reduction.
data(mtcars) analyzeMLResiduals(mpg ~ wt + qsec, mtcars)data(mtcars) analyzeMLResiduals(mpg ~ wt + qsec, mtcars)
Fits several remedial models for heteroscedasticity and compares their performance using AIC and residual RMSE. Currently evaluates weighted least squares and robust regression against the original model.
autoCompareRemediations(model, data = NULL)autoCompareRemediations(model, data = NULL)
model |
Fitted |
data |
Optional data frame if |
A list with components metrics, models, and best indicating
the recommended method.
data(mtcars) m <- lm(mpg ~ wt + qsec, mtcars) autoCompareRemediations(m)data(mtcars) m <- lm(mpg ~ wt + qsec, mtcars) autoCompareRemediations(m)
Draws one horizontal bar per test. The length of a bar is the evidence
against the null hypothesis, , on an axis labelled with
the p-values themselves, so a smaller p-value gives a longer bar. A dashed
line marks alpha; bars that pass it are drawn in the accent colour and the
others in grey. The p-value of each test is printed beside its bar, so no
reading depends on colour.
## S3 method for class 'hetero_test_suite' autoplot(object, ..., alpha = 0.05) ## S3 method for class 'hetero_grouped_suite' autoplot(object, ..., alpha = 0.05)## S3 method for class 'hetero_test_suite' autoplot(object, ..., alpha = 0.05) ## S3 method for class 'hetero_grouped_suite' autoplot(object, ..., alpha = 0.05)
object |
|
... |
Unused. |
alpha |
Significance level marked by the dashed line. Defaults to
|
Bars stop at : extra length beyond that would only
compress the tests that are near the threshold. Labels give the p-value to
three decimals, and p < 0.001 below that. A test that failed has no bar
and is labelled as such.
For a grouped suite there is one panel per group.
A ggplot object.
Up to 0.12.0 the bars were the p-values themselves on a linear axis from 0 to 1, so a test that rejected had no visible bar, and the highlighting of significant tests was never applied to a suite of more than one test.
fit <- lm(mpg ~ wt + qsec, data = mtcars) suite <- runHeteroTests( fit, mtcars, tests = c("white", "breusch_pagan", "koenker"), progress = FALSE ) ggplot2::autoplot(suite)fit <- lm(mpg ~ wt + qsec, data = mtcars) suite <- runHeteroTests( fit, mtcars, tests = c("white", "breusch_pagan", "koenker"), progress = FALSE ) ggplot2::autoplot(suite)
Chooses between no transformation, log, square root and Box–Cox based on the Breusch-Pagan test statistic.
autoTransform(model)autoTransform(model)
model |
A fitted model of class |
A list with elements model (the transformed fit) and
method indicating the chosen transformation.
data(mtcars) m <- lm(mpg ~ wt + qsec, data = mtcars) autoTransform(m)data(mtcars) m <- lm(mpg ~ wt + qsec, data = mtcars) autoTransform(m)
These helpers provide reusable bootstrap and power-estimation routines
for the heteroscedasticity testing framework. They support the robust
implementations introduced in robust_implementations.R but are
written generically so additional tests can reuse them.
Avoids recomputing expensive diagnostics by hashing their inputs and reusing stored results.
cachedTest(test_name, model, data, ..., use_cache = TRUE)cachedTest(test_name, model, data, ..., use_cache = TRUE)
test_name |
Character scalar naming the diagnostic registered in
|
model |
Fitted model object supplied to the diagnostic. |
data |
Data frame used to fit the model. |
... |
Additional arguments forwarded to the diagnostic. |
use_cache |
Logical scalar indicating whether cached results may be used
(defaults to |
The cache key is created by hashing the test name, model coefficients,
residuals, data, and additional arguments. When the key already exists in the
cache environment the stored result is returned immediately; otherwise the
diagnostic is executed and its output stored for future calls. Set
use_cache = FALSE to force recomputation when the underlying model has
changed.
The diagnostic result, either retrieved from cache or freshly computed.
clearTestCache() resets the cache between analysis sessions.
Ensures that data is a data.frame. Used internally for input
validation across the package.
checkData(data)checkData(data)
data |
Object to check. |
Invisible data if valid, otherwise an error is thrown.
Checks that model is of class lm or glm.
checkModel(model)checkModel(model)
model |
An object to check. |
Invisible model if valid, otherwise an error is thrown.
Extends checkModel() with additional soft checks that flag potential
numerical issues before computationally expensive diagnostics are executed.
The helper mirrors the warnings used throughout the package and retains the
original return semantics for backward compatibility.
checkModelEnhanced(model, data = NULL)checkModelEnhanced(model, data = NULL)
model |
Fitted model supplied to subsequent diagnostics. |
data |
Optional |
The function warns when residual degrees of freedom fall below six, when a
near-perfect fit is detected (R), or when variance inflation
factors (VIFs) exceed 10. The latter threshold follows the regression
diagnostics literature (Belsley et al., 1980).
Invisibly returns model after issuing any relevant warnings.
Belsley, D. A., Kuh, E., & Welsch, R. E. (1980). Regression Diagnostics: Identifying Influential Data and Sources of Collinearity. Wiley.
checkModel(), performVIFDiagnostic(), validateTestInputs()
data(mtcars) fit <- stats::lm(mpg ~ wt + hp, data = mtcars) checkModelEnhanced(fit)data(mtcars) fit <- stats::lm(mpg ~ wt + hp, data = mtcars) checkModelEnhanced(fit)
Removes memoised outputs stored by runHeteroTests when called with
use_cache = TRUE. Useful for deterministic test runs or after mutating the
underlying data/model so cached summaries should be invalidated.
clearAnalysisCache()clearAnalysisCache()
runHeteroTests, clearTestCache
Removes all objects from the internal cache environment so that subsequent diagnostic calls recompute their statistics.
clearTestCache()clearTestCache()
cachedTest() for invoking diagnostics with memoisation.
Runs runDiagnostics for multiple models and collects test statistics.
Diagnostics that cannot be computed (for example, due to validation failures)
emit warnings and fill the corresponding entries with NA_real_. The
original error messages are preserved on the returned data frame via the
diagnostic_errors attribute.
compareModelDiagnostics(models, data = NULL, tests = c("white", "breusch_pagan"))compareModelDiagnostics(models, data = NULL, tests = c("white", "breusch_pagan"))
models |
List of fitted models or formulas. |
data |
Optional data frame when formulas are supplied. |
tests |
Diagnostics to run. |
A data frame of statistics, one row per model. Failed diagnostics are
represented by NA_real_ entries and the underlying error messages can be
retrieved from the diagnostic_errors attribute.
data(mtcars) m1 <- lm(mpg ~ wt + qsec, mtcars) m2 <- lm(mpg ~ wt + hp, mtcars) compareModelDiagnostics(list(m1, m2))data(mtcars) m1 <- lm(mpg ~ wt + qsec, mtcars) m2 <- lm(mpg ~ wt + hp, mtcars) compareModelDiagnostics(list(m1, m2))
Runs selected diagnostics for a single model and returns a tidy data frame of test statistics and p-values.
compareTestResults(model, data = NULL, tests = c("white", "breusch_pagan"))compareTestResults(model, data = NULL, tests = c("white", "breusch_pagan"))
model |
A fitted |
data |
Data frame used if |
tests |
Character vector of heteroscedasticity tests. |
Data frame with columns test, statistic, and p.value.
data(mtcars) m <- lm(mpg ~ wt + qsec, mtcars) compareTestResults(m)data(mtcars) m <- lm(mpg ~ wt + qsec, mtcars) compareTestResults(m)
This dataset contains two predictors with correlation and a response including a quadratic term. It is useful for testing diagnostics beyond heteroscedasticity.
data(diagnostic_data)data(diagnostic_data)
A data frame with 150 rows and 3 variables:
first predictor
second predictor, correlated with x1
response
Simulated via set.seed(123).
data(diagnostic_data) head(diagnostic_data)data(diagnostic_data) head(diagnostic_data)
Provides convenient access to example datasets hosted online. Currently supports the 'tips' dataset used in various tutorials.
downloadTeachingData( name = "tips", destfile = tempfile(fileext = ".csv"), quiet = FALSE )downloadTeachingData( name = "tips", destfile = tempfile(fileext = ".csv"), quiet = FALSE )
name |
Name of the dataset to download. Only "tips" is currently supported. |
destfile |
Optional path to save the downloaded dataset. Defaults to a temporary file. |
quiet |
Logical; if FALSE, informative messages are printed during the download process. |
Path to the downloaded dataset on success, or NULL invisibly if the
download fails or no internet connection is available.
# Online example (requires internet) if (curl::has_internet()) { data_path <- downloadTeachingData(quiet = TRUE) if (!is.null(data_path)) { # Use downloaded data } } # Offline example using built-in data data(mtcars) model <- lm(mpg ~ wt + hp, data = mtcars) result <- performWhiteTest(model, mtcars) print(result)# Online example (requires internet) if (curl::has_internet()) { data_path <- downloadTeachingData(quiet = TRUE) if (!is.null(data_path)) { # Use downloaded data } } # Offline example using built-in data data(mtcars) model <- lm(mpg ~ wt + hp, data = mtcars) result <- performWhiteTest(model, mtcars) print(result)
Provides a simple interface to MASS::rlm for robust estimation.
fitRobust(model, data = NULL, ...)fitRobust(model, data = NULL, ...)
model |
A fitted model of class |
data |
Optional data frame if |
... |
Additional arguments passed to |
An object of class rlm.
data(mtcars) m <- fitRobust(mpg ~ wt + qsec, mtcars) summary(m)data(mtcars) m <- fitRobust(mpg ~ wt + qsec, mtcars) summary(m)
Refit a model by feasible generalised least squares, weighting each observation by the inverse of an estimated error variance.
fitWLS( model, data = NULL, var_formula = NULL, form = c("exponential", "power") )fitWLS( model, data = NULL, var_formula = NULL, form = c("exponential", "power") )
model |
A fitted model of class |
data |
Optional base::data.frame holding the variables named in
|
var_formula |
One-sided formula naming the variance regressors, for
example |
form |
Character scalar choosing the variance function:
|
The variance is modelled, not read off the residuals directly. A single
squared residual is a one-degree-of-freedom estimate of and
far too noisy to invert: weighting by hands almost all of the
weight to whichever observations the initial fit happened to reproduce most
closely. This function instead fits a variance function to the squared
residuals and takes from its fitted values, the
standard feasible-GLS recipe; weights are .
A new lm object fitted with weights. The estimated variances are
attached as the "variance_model" attribute, and the fitted variance
function (its form, regressors and coefficients) as the
"variance_function" attribute, which is what
performVarianceFormTest() reads.
form chooses the shape of the variance function and var_formula the
variables it depends on. Both forms are linear in the logarithm
of the variance and carry their own constant.
"exponential",
the multiplicative model of Harvey (1976), estimated by regressing
on . The log scale keeps the fitted variances
positive without constraining the auxiliary regression. This is the
default, and with var_formula = NULL it is what fitWLS() has
computed since 0.9.0.
"power", that is , the
model of Park (1966). It is the exponential form in the logarithms of
the regressors, which must be strictly positive. is the
textbook case of a standard deviation proportional to .
Other log-linear shapes are written through var_formula, for example
~ x + I(x^2) or ~ sqrt(x). The additive model
is not offered: nothing keeps
its fitted variances positive, and in the validation study it was not
usable in a material share of samples drawn from an additive model itself
(inst/validation/README.md).
Residuals that are numerically zero are floored before the logarithm is taken, with a warning.
Weights estimated this way are consistent under a correctly specified
variance function, so standard errors from the returned fit are usable. They
were not before 0.9.0, when the weights were the raw inverse squared
residuals: the weighted residual sum of squares then collapsed towards
regardless of the data, and nominal 95% intervals covered the truth
about 10% of the time.
Whether the variance function is correctly specified can be tested: pass
the result to performVarianceFormTest().
If the variance function cannot be fitted, or yields no usable variation, the function falls back to equal weights, which reduces the result to the original OLS fit.
The weighted fit keeps the design and the offset of model, whether the
offset was given as an argument, lm(..., offset = o), or written in the
formula, offset(o). Its coefficients, fitted values and residuals are
those lm() returns for the same call with the estimated weights added.
On a model fitted with weights, the refit uses the estimated weights in
their place, and weights() of the result returns them.
Harvey, A. C. (1976). Estimating regression models with multiplicative heteroscedasticity. Econometrica, 44(3), 461–465. doi:10.2307/1913974
Park, R. E. (1966). Estimation with heteroscedastic error terms. Econometrica, 34(4), 888. doi:10.2307/1910108
performVarianceFormTest() to test the variance function that was
fitted.
data(mtcars) m <- lm(mpg ~ wt + qsec, data = mtcars) wls <- fitWLS(m) summary(wls) # Variance proportional to a power of one regressor wls_power <- fitWLS(m, var_formula = ~ wt, form = "power") attr(wls_power, "variance_function")$coefficientsdata(mtcars) m <- lm(mpg ~ wt + qsec, data = mtcars) wls <- fitWLS(m) summary(wls) # Variance proportional to a power of one regressor wls_power <- fitWLS(m, var_formula = ~ wt, form = "power") attr(wls_power, "variance_function")$coefficients
Creates a standalone report summarizing heteroscedasticity tests and diagnostic plots for a fitted model.
generateDiagnosticReport( model, data = NULL, output_format = "html", output_file = NULL, include_remediation = TRUE, include_theory = FALSE )generateDiagnosticReport( model, data = NULL, output_format = "html", output_file = NULL, include_remediation = TRUE, include_theory = FALSE )
model |
Fitted |
data |
Optional data frame if |
output_format |
One of |
output_file |
Path to write the report to. If |
include_remediation |
Logical; include remediation suggestions if |
include_theory |
Logical; include background theory section. |
Invisibly returns the path to the generated report.
if (requireNamespace("rmarkdown", quietly = TRUE) && rmarkdown::pandoc_available()) { model <- lm(mpg ~ wt + hp, data = mtcars) generateDiagnosticReport( model, mtcars, output_file = file.path(tempdir(), "diagnostic_report.html") ) }if (requireNamespace("rmarkdown", quietly = TRUE) && rmarkdown::pandoc_available()) { model <- lm(mpg ~ wt + hp, data = mtcars) generateDiagnosticReport( model, mtcars, output_file = file.path(tempdir(), "diagnostic_report.html") ) }
These helpers assemble an end-to-end recommendation workflow that profiles the input dataset, selects appropriate heteroscedasticity diagnostics, interprets results with qualitative confidence labels, and suggests remediation strategies with decision-tree style guidance.
analyseDatasetCharacteristics(data, response = NULL) suggestDiagnosticsForProfile(profile) interpretHeteroTestResults(test_results, alpha = 0.05) recommendRemediationStrategies(test_results, model, data, profile = NULL) warnDiagnosticAssumptions(profile, interpretations, model, data, test_results) buildDiagnosticDecisionTree(profile, recommendations) composeDiagnosticNarrative(profile, interpretations, remediation, assumption_warnings, decision_tree) generateHeteroRecommendations(model, data = NULL, test_results = NULL, alpha = 0.05, include_report = TRUE)analyseDatasetCharacteristics(data, response = NULL) suggestDiagnosticsForProfile(profile) interpretHeteroTestResults(test_results, alpha = 0.05) recommendRemediationStrategies(test_results, model, data, profile = NULL) warnDiagnosticAssumptions(profile, interpretations, model, data, test_results) buildDiagnosticDecisionTree(profile, recommendations) composeDiagnosticNarrative(profile, interpretations, remediation, assumption_warnings, decision_tree) generateHeteroRecommendations(model, data = NULL, test_results = NULL, alpha = 0.05, include_report = TRUE)
data |
A |
response |
Optional response variable name used for labelling. |
profile |
Dataset profile produced by
|
test_results |
Named list of |
alpha |
Significance level applied when interpreting p-values. |
model |
Fitted |
interpretations |
Output from |
recommendations |
Output from |
remediation |
Output from |
assumption_warnings |
Character vector of generated warnings. |
decision_tree |
Data frame returned by
|
include_report |
Logical; include a plain-language narrative in the output. |
The recommendation engine analyses dataset characteristics such as sample size, missingness, and predictor skewness to propose diagnostics tailored to the context. It automatically interprets test outcomes, attaches qualitative confidence labels, warns when assumptions are at risk, and suggests remediation strategies matched to detected variance patterns. The generated decision tree and narrative target non-specialist audiences who need actionable guidance.
analyseDatasetCharacteristics() returns a list describing dataset size,
missingness, skewness, and risk factors. suggestDiagnosticsForProfile()
returns a data frame of recommended diagnostics with rationales.
interpretHeteroTestResults() yields a tidy data frame of interpretations
and an overall summary. recommendRemediationStrategies() produces a
structured remediation plan. warnDiagnosticAssumptions() returns
warnings about assumption violations. buildDiagnosticDecisionTree()
constructs a tidy decision tree. composeDiagnosticNarrative() outputs a
plain-language character vector, and generateHeteroRecommendations()
returns an object of class hetero_recommendation_report bundling all
components.
runHeteroTests(), suggestRemediation(),
generateDiagnosticReport()
model <- lm(mpg ~ wt + hp, data = mtcars) recs <- generateHeteroRecommendations(model, mtcars) print(recs)model <- lm(mpg ~ wt + hp, data = mtcars) recs <- generateHeteroRecommendations(model, mtcars) print(recs)
This dataset is generated from the model ,
where . A fixed seed ensures repeatable values.
data(hetero_data)data(hetero_data)
A data frame with 100 rows and 2 variables:
predictor
response
Simulated with set.seed(42); runif() and rnorm().
data(hetero_data) plot(hetero_data$x, hetero_data$y)data(hetero_data) plot(hetero_data$x, hetero_data$y)
Collections of heteroscedasticity test results returned by runHeteroTests.
A hetero_test_suite is a simple named list of htest objects with
additional metadata. When diagnostics are evaluated on grouped data, the
returned object inherits from hetero_grouped_suite and contains one
hetero_test_suite per group along with the grouping keys.
These classes are primarily useful for method dispatch (e.g. the broom tidiers
and autoplot() methods). Users typically interact with the objects via
generics::tidy(), generics::glance(), generics::augment()
and ggplot2::autoplot().
Create a diagnostic object that exposes test(), plot() and summary() methods. Formulas are accepted for convenience.
HeteroDiagnostic(model, data = NULL)HeteroDiagnostic(model, data = NULL)
model |
A fitted lm or glm object, or a formula. |
data |
Data used to fit the model when |
An object of class HeteroDiagnostic.
data(mtcars) m <- lm(mpg ~ wt + qsec, data = mtcars) d <- HeteroDiagnostic(m, mtcars) test(d)data(mtcars) m <- lm(mpg ~ wt + qsec, data = mtcars) d <- HeteroDiagnostic(m, mtcars) test(d)
These helpers manage the package-level logging subsystem used to debug complex diagnostic workflows. Users can adjust verbosity, enable log capture, inspect recent log entries and clear the stored history when finished.
ht_set_log_level(level = c("INFO", "WARN", "ERROR", "SILENT")) ht_enable_log_capture(enabled = TRUE, max_entries = 1000L, sink = NULL) ht_log_history() ht_clear_log_history()ht_set_log_level(level = c("INFO", "WARN", "ERROR", "SILENT")) ht_enable_log_capture(enabled = TRUE, max_entries = 1000L, sink = NULL) ht_log_history() ht_clear_log_history()
level |
Character string specifying the minimum level to emit. Accepted values are "INFO", "WARN", "ERROR" and "SILENT". |
enabled |
Logical flag, |
max_entries |
Maximum number of entries to retain in memory. Older entries are discarded first.
Use |
sink |
Optional file path or connection to mirror log output. |
ht_set_log_level() returns the previous log level invisibly.
ht_enable_log_capture() and ht_clear_log_history() return NULL.
ht_log_history() returns a data frame with columns timestamp, level and message.
Launch a production-ready Shiny dashboard for running heteroscedasticity diagnostics, exploring interactive plots, and experimenting with simulation studies.
launchDiagnosticDashboard(model, data)launchDiagnosticDashboard(model, data)
model |
Fitted |
data |
Data frame used to fit the model. |
Requires optional packages shiny, DT, and plotly. Excel uploads additionally depend on readxl and exporting interactive graphics relies on htmlwidgets. The dashboard guides users through data preparation, model fitting, diagnostic testing, interactive Plotly visualisations, and a real-time simulation lab for exploring heteroscedastic data-generating processes. Download buttons are provided for both results tables and interactive plots.
A shiny.appobj that can be run with shiny::runApp().
if (interactive() && requireNamespace("shiny", quietly = TRUE) && requireNamespace("DT", quietly = TRUE) && requireNamespace("plotly", quietly = TRUE)) { mod <- lm(mpg ~ wt + hp, data = mtcars) launchDiagnosticDashboard(mod, mtcars) }if (interactive() && requireNamespace("shiny", quietly = TRUE) && requireNamespace("DT", quietly = TRUE) && requireNamespace("plotly", quietly = TRUE)) { mod <- lm(mpg ~ wt + hp, data = mtcars) launchDiagnosticDashboard(mod, mtcars) }
Returns the names runHeteroTests() accepts in tests: the diagnostics
the package registers and any added with registerDiagnostic().
listDiagnostics()listDiagnostics()
"box_m" is registered for runMultivariateTests(), which calls it with
data and a grouping factor rather than with a model.
A character vector of the registered names, sorted.
registerDiagnostic(), runHeteroTests()
listDiagnostics()listDiagnostics()
Collection of advanced heteroscedasticity tests including wild bootstrap, heteroscedasticity-consistent covariance LM statistics, quantile regression comparisons, rank-based permutation checks, high-dimensional projections and spatial correlation diagnostics.
modern_diagnosticsmodern_diagnostics
An object of class NULL of length 0.
Regresses squared residuals on their lags to detect ARCH effects.
performArchLMTest(model, lags = 1)performArchLMTest(model, lags = 1)
model |
an object of class |
lags |
number of lags to include. |
The statistic is from an auxiliary regression of on its lagged values, where is the coefficient of determination. Under the null of no ARCH effects it follows a chi-square distribution with degrees of freedom equal to the number of lags.
An object of class htest containing the test statistic, p-value and degrees of freedom.
Engle, R. F. (1982). Autoregressive conditional heteroskedasticity with estimates of the variance of United Kingdom inflation. Econometrica, 50(4), 987–1007. doi:10.2307/1912773
Hamilton, J. D. (1994). Time Series Analysis. Princeton University Press.
data(mtcars) m <- lm(mpg ~ wt + qsec, data = mtcars) performArchLMTest(m, lags = 2)data(mtcars) m <- lm(mpg ~ wt + qsec, data = mtcars) performArchLMTest(m, lags = 2)
Uses bartlett.test on model residuals grouped by a factor.
performBartlettTest(model, data, group)performBartlettTest(model, data, group)
model |
an object of class |
data |
data frame used to fit |
group |
name of the grouping variable. |
The test statistic compares the pooled variance to the individual group variances. It is computed as , where is the pooled variance and the group variances. Under the null it approximates a chi-square distribution with degrees of freedom.
An object of class htest containing the chi-squared statistic, p-value and degrees of freedom.
Bartlett, M. S. (1937). Properties of sufficiency and statistical tests. Proceedings of the Royal Society of London, 160(901), 268–282. doi:10.1098/rspa.1937.0109
Hartley, H. O. (1950). The maximum F-ratio as a short-cut test for heterogeneity of variance. Biometrika, 37(3/4), 308–312. doi:10.2307/2332383
data(mtcars) mtcars$cyl <- factor(mtcars$cyl) m <- lm(mpg ~ wt, data = mtcars) performBartlettTest(m, mtcars, "cyl")data(mtcars) mtcars$cyl <- factor(mtcars$cyl) m <- lm(mpg ~ wt, data = mtcars) performBartlettTest(m, mtcars, "cyl")
Test whether multiple groups have equal covariance matrices.
performBoxMTest(data, group)performBoxMTest(data, group)
data |
A numeric data frame or matrix. |
group |
A factor indicating group membership. |
An object of class htest.
data(iris) performBoxMTest(iris[,1:4], iris$Species)data(iris) performBoxMTest(iris[,1:4], iris$Species)
Lagrange Multiplier test for the presence of a random individual effect in panel data. This is not a test for heteroscedasticity and does not respond to one; use the auxiliary-regression diagnostics for that.
performBPRandomEffectsTest(model, data, id)performBPRandomEffectsTest(model, data, id)
model |
an object of class |
data |
data frame used to fit |
id |
individual identifier column. |
The statistic is Breusch and Pagan (1980) equation 5, , which follows a chi-square distribution with one degree of freedom under the null of no individual effect. The bracketed ratio is close to one under the null and the statistic measures its squared departure from one. Before 0.11.0 the "- 1" and the square were absent and the scaling used T^2 rather than nT, which left the statistic sitting at the critical value: it rejected about a third of the time when no individual effect was present.
An object of class htest.
Breusch, T. S., & Pagan, A. R. (1980). The Lagrange Multiplier Test and Its Applications to Model Specification in Econometrics. Review of Economic Studies, 47(1), 239–253.
df <- data.frame(id = rep(1:5, each = 4), time = rep(1:4, 5), x = runif(20), y = rnorm(20)) m <- lm(y ~ x, data = df) performBPRandomEffectsTest(m, df, "id")df <- data.frame(id = rep(1:5, each = 4), time = rep(1:4, 5), x = runif(20), y = rnorm(20)) m <- lm(y ~ x, data = df) performBPRandomEffectsTest(m, df, "id")
Implements the classical Breusch-Pagan (1979) test on a fitted linear model, in which the scaled squared residuals are regressed on the original regressors.
performBPTest(model, data) performBreuschPaganTest(model, data)performBPTest(model, data) performBreuschPaganTest(model, data)
model |
an object of class |
data |
data frame used to fit |
The test statistic is half the explained sum of squares from regressing the scaled squared residuals (with ) on the explanatory variables. Under the null hypothesis of homoscedasticity and normal disturbances it follows a chi-square distribution with degrees of freedom equal to the number of regressors, matching lmtest::bptest(..., studentize = FALSE). For the studentized form that drops the normality assumption use performKoenkerTest or performStudentizedBPTest.
An object of class htest containing the test statistic, p-value and degrees of freedom.
On a fit with weights the test is computed from the Pearson residuals , so it tests whether the weights are adequate; see the section on weighted fits in performKoenkerTest(), which also covers weights estimated by fitWLS().
Breusch, T. S., & Pagan, A. R. (1979). A simple test for heteroscedasticity and random coefficient variation. Econometrica, 47(5), 1287–1294. doi:10.2307/1911963
Koenker, R. (1981). A note on studentizing a test for heteroscedasticity. Journal of Econometrics, 17(1), 107–112. doi:10.1016/0304-4076(81)90062-2
data(mtcars) m <- lm(mpg ~ wt + qsec, data = mtcars) performBPTest(m, mtcars)data(mtcars) m <- lm(mpg ~ wt + qsec, data = mtcars) performBPTest(m, mtcars)
Enhances performBPTest() by optionally studentising residuals, resampling the
test statistic via bootstrap, and reporting effect sizes together with power
diagnostics.
performBPTestRobust( model, data, studentized = TRUE, bootstrap = FALSE, B = 1000, ci_level = 0.95, parallel = FALSE )performBPTestRobust( model, data, studentized = TRUE, bootstrap = FALSE, B = 1000, ci_level = 0.95, parallel = FALSE )
model |
A fitted stats::lm object describing the mean structure whose residual variance is to be assessed. |
data |
A base::data.frame (or compatible object) containing the
variables referenced in |
studentized |
Logical, use studentized residuals for the auxiliary
regression (Koenker variant)? Defaults to |
bootstrap |
Logical, compute bootstrap diagnostics for the statistic and p-value? |
B |
Number of bootstrap replications when |
ci_level |
Confidence level for reported intervals. |
parallel |
Logical, allow parallel bootstrap evaluation when the
|
Offers expanded reporting for the Breusch–Pagan family of tests including
bootstrap p-values and asymptotic confidence intervals. The optional
studentized argument toggles between the classic and Koenker versions.
An augmented htest object containing a
robust_details element describing the additional diagnostics.
Breusch, T. S., & Pagan, A. R. (1979). A simple test for heteroscedasticity and random coefficient variation. Econometrica, 47(5), 1287–1294.
Koenker, R. (1981). A note on studentizing a test for heteroscedasticity. Journal of Econometrics, 17(1), 107–112.
performBPTest() for the baseline test and performStudentizedBPTest() for the
standalone studentised variant.
data(mtcars) mod <- lm(mpg ~ wt + qsec, data = mtcars) performBPTestRobust(mod, mtcars, bootstrap = TRUE, B = 200)data(mtcars) mod <- lm(mpg ~ wt + qsec, data = mtcars) performBPTestRobust(mod, mtcars, bootstrap = TRUE, B = 200)
Computes the classical Breusch\–Pagan statistic using chunked cross-products so
that large datasets can be evaluated without materialising the full auxiliary
regression in memory. The streamed result is algebraically identical to
performBPTest.
performBPTestStreaming(model, data, chunk_size = 10000, progress = interactive())performBPTestStreaming(model, data, chunk_size = 10000, progress = interactive())
model |
A fitted stats::lm object describing the mean structure whose residual variance is to be assessed. |
data |
A base::data.frame containing the variables referenced in
|
chunk_size |
Positive integer giving the number of observations processed per streaming chunk. Smaller values reduce peak memory usage at the expense of additional iteration overhead. |
progress |
Logical flag controlling whether a textual progress bar is displayed
while chunks are processed. Defaults to |
Each chunk contributes to the cross-product matrices and for the
auxiliary regression of squared residuals on the original regressors. The
chunks are aggregated to recover the exact Breusch\–Pagan statistic while keeping
memory usage bounded. When Matrix is installed, sparse cross-products are
used automatically for large chunks.
A htest object mirroring performBPTest and reporting the
chi-squared statistic, degrees of freedom, p-value, and metadata describing the
chunked computation.
performBPTest for the standard implementation.
data(mtcars) mod <- lm(mpg ~ wt + qsec, data = mtcars) performBPTestStreaming(mod, mtcars, chunk_size = 16, progress = FALSE)data(mtcars) mod <- lm(mpg ~ wt + qsec, data = mtcars) performBPTestStreaming(mod, mtcars, chunk_size = 16, progress = FALSE)
Brown-Forsythe test using medians instead of means.
performBrownForsytheTest(model, data, group)performBrownForsytheTest(model, data, group)
model |
an object of class |
data |
data frame used to fit |
group |
name of the grouping variable. |
The absolute deviations from the group medians are compared across groups. The resulting statistic is an ratio with and degrees of freedom.
An object of class htest containing the F statistic, p-value and degrees of freedom.
Brown, M. B., & Forsythe, A. B. (1974). Robust tests for the equality of variances. Journal of the American Statistical Association, 69(346), 364–367.
data(mtcars) mtcars$cyl <- factor(mtcars$cyl) m <- lm(mpg ~ wt, data = mtcars) performBrownForsytheTest(m, mtcars, "cyl")data(mtcars) mtcars$cyl <- factor(mtcars$cyl) m <- lm(mpg ~ wt, data = mtcars) performBrownForsytheTest(m, mtcars, "cyl")
The Cook-Weisberg (1983) score test with the fitted values as the sole variance regressor.
performCookWeisbergTest(model)performCookWeisbergTest(model)
model |
an object of class |
Writing for the maximum-likelihood error variance, the test regresses the scaled squared residuals on the fitted values and refers half the explained sum of squares to a chi-square distribution with one degree of freedom. This is the diagnostic returned by Stata's estat hettest with the fitted option, and it is exactly performNCVTest with its default variance model.
The chi-square reference distribution follows from the null variance of being 2, which holds under normal errors. When that assumption is doubtful, prefer performKoenkerTest.
An object of class htest containing the score statistic, its single degree of freedom and the p-value.
Reproduces car::ncvTest() to within 1e-8; see ‘tests/testthat/test-pass-a-reference.R’. Releases before 0.7.0 returned from regressing the raw squared residuals on the fitted values, which is the studentized (Koenker) statistic rather than the Cook-Weisberg score test.
Cook, R. D., & Weisberg, S. (1983). Diagnostics for heteroscedasticity in regression. Biometrika, 70(1), 1–10. doi:10.1093/biomet/70.1.1
performNCVTest, performKoenkerTest, performBPTest
data(mtcars) m <- lm(mpg ~ wt + qsec, data = mtcars) performCookWeisbergTest(m)data(mtcars) m <- lm(mpg ~ wt + qsec, data = mtcars) performCookWeisbergTest(m)
Regresses log(residual^2) on fitted values using a polynomial.
performDavidianCarrollTest(model, degree = 2)performDavidianCarrollTest(model, degree = 2)
model |
an object of class |
degree |
polynomial degree. |
A polynomial in the fitted values is fitted to . Joint significance of the polynomial terms is evaluated with an statistic.
An object of class htest.
Davidian, M., & Carroll, R. J. (1987). Variance function estimation. Journal of the American Statistical Association, 82(400), 1079–1091.
data(mtcars) m <- lm(mpg ~ wt + qsec, data = mtcars) performDavidianCarrollTest(m)data(mtcars) m <- lm(mpg ~ wt + qsec, data = mtcars) performDavidianCarrollTest(m)
Non-parametric test based on ranks.
performFlignerKilleenTest(model, data, group)performFlignerKilleenTest(model, data, group)
model |
an object of class |
data |
data frame used to fit |
group |
name of the grouping variable. |
Absolute residuals are ranked after adjusting for group medians. The statistic approximates a chi-square distribution with degrees of freedom.
An object of class htest containing the chi-squared statistic, p-value and degrees of freedom.
Fligner, M. A., & Killeen, T. J. (1976). Distribution-free two-sample tests for scale. Journal of the American Statistical Association, 71(353), 210–213.
data(mtcars) mtcars$cyl <- factor(mtcars$cyl) m <- lm(mpg ~ wt, data = mtcars) performFlignerKilleenTest(m, mtcars, "cyl")data(mtcars) mtcars$cyl <- factor(mtcars$cyl) m <- lm(mpg ~ wt, data = mtcars) performFlignerKilleenTest(m, mtcars, "cyl")
Regresses absolute residuals on a transformation of a suspected variable. With robust = TRUE the test is the version of Im (2000) and of Machado and Santos Silva (2000), which keeps its level when the errors are asymmetric.
performGlejserTest(model, data, variable, transformation = c("abs", "sqrt", "inverse", "inverse_sqrt"), robust = FALSE)performGlejserTest(model, data, variable, transformation = c("abs", "sqrt", "inverse", "inverse_sqrt"), robust = FALSE)
model |
an object of class |
data |
data frame used to fit |
variable |
name of the suspected variable. |
transformation |
transformation applied to |
robust |
logical. When |
A variety of transformations of the explanatory variable (e.g. absolute value, square root) can reveal a relationship between scale and the covariate. Significance of the slope parameter is assessed with a t test. For a weighted fit the residuals are the Pearson residuals.
The default statistic has its nominal level when positive and negative errors are equally likely. Use robust = TRUE when the residuals are skewed or their shape is unknown.
Either form conditions on one variable and one transformation. Scanning several transformations and reporting only the smallest p-value invalidates the nominal level. Simulated size and power are recorded in inst/validation/pass-a-size-power.csv for the default and in inst/validation/glejser-skewed-errors.csv for both.
An object of class htest containing the t statistic, p-value and degrees of freedom. The method element says which of the two statistics was computed.
Glejser's statistic takes the absolute residuals for the absolute errors. The two differ by the estimation error of the mean equation,
and the second term averages out only when positive and negative errors are equally likely (Godfrey 1996). When they are not, and the variable tested is correlated with the regressors, the test does not in general have its nominal level, and a larger sample does not help. In the designs of inst/validation/glejser-skewed-errors.R the default statistic rejects a true null hypothesis about 13% of the time at the 5% level under exponential errors and about 17% under lognormal errors, at every sample size from 50 to 1000. For other error distributions the rate can also fall below the nominal level.
robust = TRUE replaces the regressand by
where is the proportion of positive residuals less the proportion of negative ones. This is the correction of Im (2000). The regressand of Machado and Santos Silva (2000), with the proportion of non-negative residuals, is half of it when no residual is exactly zero, and the two then give the same test. A residual that is zero up to rounding error is counted as zero, so that the statistic does not depend on the sign of a rounding error.
The auxiliary regression is otherwise the same. Both references state the statistic as of that regression, referred to a chi-squared distribution with one degree of freedom. The t statistic reported here is the signed form of it, , and its p-value is taken from the t distribution with degrees of freedom, as for the default. The two p-values agree as the sample grows.
In the same study the corrected statistic is within simulation error of the 5% level from 150 observations on. At 50 observations it rejects 5.7% to 6.6% of the time under skewed errors. Under symmetric errors is close to zero and the two statistics differ little: the corrected one rejects about half a percentage point less often at 50 observations and gives up one or two points of power there. For a weighted fit the correction is applied to the Pearson residuals.
Glejser, H. (1969). A new test for heteroskedasticity. Journal of the American Statistical Association, 64(325), 316–323.
Godfrey, L. G. (1996). Some results on the Glejser and Koenker tests for heteroskedasticity. Journal of Econometrics, 72(1–2), 275–299. doi:10.1016/0304-4076(94)01722-0
Im, K. S. (2000). Robustifying Glejser test of heteroskedasticity. Journal of Econometrics, 97(1), 179–188. doi:10.1016/S0304-4076(99)00061-5
Machado, J. A. F. and Santos Silva, J. M. C. (2000). Glejser's test revisited. Journal of Econometrics, 97(1), 189–202. doi:10.1016/S0304-4076(00)00016-6
performKoenkerTest for a test on the squared residuals that needs neither normal nor symmetric errors; performParkTest and performHarveyTest for related parametric tests.
data(mtcars) m <- lm(mpg ~ wt + qsec, data = mtcars) performGlejserTest(m, mtcars, "wt") # The version that keeps its level under asymmetric errors performGlejserTest(m, mtcars, "wt", robust = TRUE) # Examine an alternative transformation performGlejserTest(m, mtcars, "wt", transformation = "inverse")data(mtcars) m <- lm(mpg ~ wt + qsec, data = mtcars) performGlejserTest(m, mtcars, "wt") # The version that keeps its level under asymmetric errors performGlejserTest(m, mtcars, "wt", robust = TRUE) # Examine an alternative transformation performGlejserTest(m, mtcars, "wt", transformation = "inverse")
Implements the Goldfeld-Quandt test on a fitted linear model with directional or two-sided alternatives.
performGQTest(model, data, order_by, fraction = 0.2, alternative = c("greater", "two.sided", "less"))performGQTest(model, data, order_by, fraction = 0.2, alternative = c("greater", "two.sided", "less"))
model |
an object of class |
data |
data frame used to fit |
order_by |
single column name used to order observations. |
fraction |
fraction of observations omitted from the middle; must lie strictly between zero and one. |
alternative |
alternative hypothesis: |
Observations are ordered by a suspected variance-driving variable. With the split point fixed at the sample midpoint, a central fraction is omitted and the original model is re-estimated on the lower and upper segments. The statistic is the residual mean square of segment 2 divided by the residual mean square of segment 1 and is therefore directional rather than being forced above one. Split arithmetic and p-value conventions match lmtest::gqtest(..., point = 0.5).
An object of class htest containing the directional GQ statistic, p-value, degrees of freedom and alternative hypothesis.
On a fit with weights each segment is refitted with its own weights and the segments are compared on the weighted residual sum of squares, . That is the Goldfeld-Quandt statistic of the equivalent unweighted regression, so the test asks whether the weights are adequate. Releases before 0.12.0 refitted the segments without the weights.
Goldfeld, S. M., & Quandt, R. E. (1965). Some tests for homoscedasticity. Journal of the American Statistical Association, 60(310), 539–547. doi:10.1080/01621459.1965.10480811
Greene, W. H. (2018). Econometric Analysis (8th ed.). Pearson.
data(mtcars) m <- lm(mpg ~ wt + qsec, data = mtcars) performGQTest(m, mtcars, order_by = "wt") performGQTest(m, mtcars, order_by = "wt", alternative = "two.sided")data(mtcars) m <- lm(mpg ~ wt + qsec, data = mtcars) performGQTest(m, mtcars, order_by = "wt") performGQTest(m, mtcars, order_by = "wt", alternative = "two.sided")
Orders the observations by a variable and tests whether the share of the residual sum of squares that falls in the first part of the ordered sample is too small, or too large, for errors of constant variance. The p-value is exact under normal errors, given the regressors.
performHarrisonMcCabeTest( model, data, order_by, point = 0.5, alternative = c("less", "two.sided", "greater") )performHarrisonMcCabeTest( model, data, order_by, point = 0.5, alternative = c("less", "two.sided", "greater") )
model |
A fitted stats::lm object, with or without weights. |
data |
A base::data.frame containing the variables used to fit
|
order_by |
Character scalar naming the column of |
point |
The size of the first part of the ordered sample. A number
strictly between 0 and 1 is a fraction of the sample, and the first part
then holds |
alternative |
Character scalar. |
With the
least-squares residuals in the order of order_by, the statistic of
Harrison and McCabe (1979) is
the share of the residual sum of squares that falls in the first
observations. A variance that increases along the ordering makes
small, and one that decreases makes it large. It is the statistic of
lmtest::hmctest().
The 1979 article was not consulted for this implementation. The definition
follows Harrison (1981), by its first author, which restates the statistic
with the integer part of and rejects for small
, and it agrees with lmtest::hmctest().
Under normal errors of constant variance, is a ratio of quadratic
forms in normal variables, and its distribution depends on the regressors.
With the residual-maker of the design in the ordered sample and
the diagonal matrix that selects the first observations,
where the are independent standard normal and the
are the eigenvalues of on the
residual space, being the number of coefficients. They are found
from the singular values of the first rows of an
orthonormal basis of the design, and the probability is evaluated by
Imhof's (1961) formula with stats::integrate(), as Harrison (1981) does
for the exact variant of the test. For a constant and a linear trend, the
5% critical values this gives at 10, 20, 30 and 40 observations are those
of Harrison's (1981) Table 3 to the three decimals printed there. Under the
null hypothesis the mean of is
,
with the leverages in the ordered sample.
The probability is computed to an absolute accuracy of about 2e-11.
Smaller p-values are not resolved, and a statistic far in a tail can return
a p-value of 0.
The p-value depends only on the space spanned by the regressors, so it does not change with the parametrisation of the model.
An object of class htest with the share HMC as the
statistic, the number of observations in the first part m and the sample
size n as parameters, the p-value, and the alternative in words.
In performGQTest() and performSzroeterTest() the statistic grows when
the variance increases along the ordering, and in this test it shrinks. The
alternative names the tail of each statistic, so the same hypothesis, a
variance that increases with order_by, is alternative = "less" here and
alternative = "greater" in those two functions. In all three it is the
default, and the alternative element of the result states it in words.
On a fit with weights the statistic is computed from the Pearson residuals
, and the null distribution from
the weighted design . Both are those of
the equivalent unweighted regression, so the test asks whether the weights
are adequate.
The null distribution assumes normal errors. In the designs of
inst/validation/harrison-mccabe-size-power.R the test rejects a true null
hypothesis 11.7% to 16.3% of the time at the 5% level when the errors
follow a distribution, and more often the larger the sample;
performGQTest() and performSzroeterTest() do the same. When the tails
may be heavy, use performGlejserTest() with the ordering variable as
variable and robust = TRUE, which in the same study rejects 4.7% to
4.9% of the time under those errors. Its default transformation takes the
absolute value of the variable, which preserves the ordering only when the
variable is positive.
The statistic agrees with lmtest::hmctest() to 1e-8. Its p-value
does not: with simulate.p = TRUE it is simulated from residuals of a
regression on a constant alone, whatever the model, and with
simulate.p = FALSE it is NA. skedastic::harrison_mccabe() reports a
different p-value as well; inst/validation/README.md says why.
Harrison, M. J. (1981). A comparison of the bounds, beta-approximate, and exact variants of two tests for heteroscedasticity based on ordinary least squares residuals. The Economic and Social Review, 12(4), 235–252.
Harrison, M. J., & McCabe, B. P. M. (1979). A test for heteroscedasticity based on ordinary least squares residuals. Journal of the American Statistical Association, 74(366a), 494–499. doi:10.1080/01621459.1979.10482544
Imhof, J. P. (1961). Computing the distribution of quadratic forms in normal variables. Biometrika, 48(3-4), 419–426. doi:10.1093/biomet/48.3-4.419
performGQTest() and performSzroeterTest() for the other tests along an
ordering of the observations; performGlejserTest() when the errors may be
heavy-tailed.
data(mtcars) mod <- lm(mpg ~ wt + qsec, data = mtcars) performHarrisonMcCabeTest(mod, mtcars, order_by = "wt") # Variance that increases with x set.seed(7) x <- runif(80, 1, 5) d <- data.frame(x = x, y = 1 + 2 * x + rnorm(80, sd = exp(0.3 * x))) performHarrisonMcCabeTest(lm(y ~ x, data = d), d, order_by = "x") # Either direction, with a third of the sample in the first part performHarrisonMcCabeTest(lm(y ~ x, data = d), d, order_by = "x", point = 1 / 3, alternative = "two.sided" )data(mtcars) mod <- lm(mpg ~ wt + qsec, data = mtcars) performHarrisonMcCabeTest(mod, mtcars, order_by = "wt") # Variance that increases with x set.seed(7) x <- runif(80, 1, 5) d <- data.frame(x = x, y = 1 + 2 * x + rnorm(80, sd = exp(0.3 * x))) performHarrisonMcCabeTest(lm(y ~ x, data = d), d, order_by = "x") # Either direction, with a third of the sample in the first part performHarrisonMcCabeTest(lm(y ~ x, data = d), d, order_by = "x", point = 1 / 3, alternative = "two.sided" )
Compares the maximum and minimum group residual variances using Hartley's maximum F-ratio distribution.
performHartleyFmaxTest(model, data, group)performHartleyFmaxTest(model, data, group)
model |
A fitted |
data |
Data frame used to fit |
group |
Name of the grouping variable. |
The statistic is . Under normality and equal group sizes its null distribution is the maximum F-ratio distribution for independent mean squares with common degrees of freedom, evaluated with SuppDists::pmaxFratio(). If group sizes differ, the function warns and rounds the mean group size, then subtracts one, to obtain an approximate common integer degrees of freedom.
An object of class htest containing the Fmax statistic, number of groups, reference degrees of freedom and p-value.
Hartley, H. O. (1950). The maximum F-ratio as a short-cut test for heterogeneity of variance. Biometrika, 37(3/4), 308–312.
set.seed(1701) n <- 20 d <- data.frame(g = factor(rep(letters[1:3], each = n)), x = rnorm(3 * n)) d$y <- 1 + d$x + rnorm(3 * n) m <- lm(y ~ x, data = d) performHartleyFmaxTest(m, d, "g")set.seed(1701) n <- 20 d <- data.frame(g = factor(rep(letters[1:3], each = n)), x = rnorm(3 * n)) d$y <- 1 + d$x + rnorm(3 * n) m <- lm(y ~ x, data = d) performHartleyFmaxTest(m, d, "g")
Harvey's (1976) Lagrange multiplier test, which regresses log(residuals^2) on a set of variance regressors.
performHarveyTest(model, auxiliary = c("regressors", "fitted"), studentize = FALSE)performHarveyTest(model, auxiliary = c("regressors", "fitted"), studentize = FALSE)
model |
an object of class |
auxiliary |
character scalar choosing the variance regressors. |
studentize |
logical; if |
Harvey (1976) models the error variance as and tests through the auxiliary regression of on . Under the null the auxiliary error behaves like a centred variate with variance , so the classical statistic is , asymptotically chi-square with degrees of freedom.
Setting studentize = TRUE replaces the fixed constant with the auxiliary residual mean square and refers the overall F statistic to an F distribution. The two forms are asymptotically equivalent under normal errors; the studentized form is more reliable when normality is doubtful, because is the null variance of only for Gaussian errors.
Degrees of freedom are taken from the realised rank of the auxiliary design, so a rank-deficient variance model is not credited with degrees of freedom for aliased columns.
An object of class htest containing the test statistic, its degrees of freedom and the p-value.
The default statistic reproduces an independent reconstruction of Harvey (1976) to within 1e-8; see ‘tests/testthat/test-pass-a-reference.R’. Simulated size and power are recorded in ‘inst/validation/pass-a-size-power.csv’.
Harvey, A. C. (1976). Estimating regression models with multiplicative heteroscedasticity. Econometrica, 44(3), 461–465. doi:10.2307/1913974
Greene, W. H. (2018). Econometric Analysis (8th ed.). Pearson. Section 9.5 derives the form of the statistic.
performParkTest, performGlejserTest, performBPTest
data(mtcars) m <- lm(mpg ~ wt + qsec, data = mtcars) performHarveyTest(m) # Studentized variant, which does not assume normal errors performHarveyTest(m, studentize = TRUE) # Variance driven by the conditional mean rather than by the regressors performHarveyTest(m, auxiliary = "fitted")data(mtcars) m <- lm(mpg ~ wt + qsec, data = mtcars) performHarveyTest(m) # Studentized variant, which does not assume normal errors performHarveyTest(m, studentize = TRUE) # Variance driven by the conditional mean rather than by the regressors performHarveyTest(m, auxiliary = "fitted")
Applies principal component projections to the design matrix and evaluates a Breusch-Pagan style statistic on the reduced representation. The procedure is designed for settings where the number of predictors rivals or exceeds the sample size.
performHighDimensionalTest( model, data, variance_threshold = 0.9, max_components = NULL )performHighDimensionalTest( model, data, variance_threshold = 0.9, max_components = NULL )
model |
A fitted stats::lm object describing the mean structure whose residual variance is to be assessed. |
data |
A base::data.frame (or compatible object) containing the
variables referenced in |
variance_threshold |
Proportion of predictor variance that the selected principal components should explain. Defaults to 0.9. |
max_components |
Optional upper bound on the number of principal
components to retain. Defaults to |
An htest object summarising the chi-squared statistic
of the auxiliary regression on principal component scores.
Fan, J., & Lv, J. (2008). Sure independence screening for ultrahigh dimensional feature space. Journal of the Royal Statistical Society: Series B, 70(5), 849–911.
set.seed(123) X <- matrix(rnorm(80 * 20), nrow = 80) beta <- c(rep(1, 5), rep(0, 15)) y <- X %*% beta + rnorm(80, sd = 0.5 + 0.2 * scale(X[, 1])) df <- as.data.frame(cbind(y = as.numeric(y), X)) model <- lm(y ~ ., data = df) performHighDimensionalTest(model, df)set.seed(123) X <- matrix(rnorm(80 * 20), nrow = 80) beta <- c(rep(1, 5), rep(0, 15)) y <- X %*% beta + rnorm(80, sd = 0.5 + 0.2 * scale(X[, 1])) df <- as.data.frame(cbind(y = as.numeric(y), X)) model <- lm(y ~ ., data = df) performHighDimensionalTest(model, df)
Uses Cook's distance to flag influential observations.
performInfluenceDiagnostics(model, cutoff = NULL)performInfluenceDiagnostics(model, cutoff = NULL)
model |
A fitted |
cutoff |
Cook's distance threshold; defaults to |
A list with Cook's distances and indices of influential points.
data(mtcars) m <- lm(mpg ~ wt + qsec, data = mtcars) performInfluenceDiagnostics(m)data(mtcars) m <- lm(mpg ~ wt + qsec, data = mtcars) performInfluenceDiagnostics(m)
Implementation of the Koenker version of the Breusch-Pagan test.
performKoenkerTest(model, data)performKoenkerTest(model, data)
model |
an object of class |
data |
data frame used to fit |
Squared residuals are regressed on the regressors but the statistic uses a studentized form that is robust to non-normality.
An object of class htest containing the test statistic, p-value and degrees of freedom.
lm(..., weights = w) states that the error variance is . On such a fit the test is computed from the Pearson residuals , the residuals of the equivalent unweighted regression, which have constant variance when the weights are right. The null hypothesis is then that the weights are adequate; the variance regressors stay on their original scale. Releases before 0.12.0 used the raw residuals, whose variance differs across observations by assumption, so a correctly weighted fit was rejected as often as an unweighted one. A fit with a zero weight is refused.
The reference distribution takes the weights as known. When they were estimated from the same data, as by fitWLS(), it is only approximate, and not more accurate in larger samples. With a correctly specified variance function and normal errors, the Koenker test rejected 8% of the time at the 5% level with 150 observations and 11% with 600, the White test 6% and 8%, and the Harvey test never, because it repeats the regression the weights were estimated from (inst/validation/weighted-fits-size.csv). performVarianceFormTest() accounts for the estimation, held its level in the same designs, and is the test to use on a fitWLS() fit.
Koenker, R. (1981). A note on studentizing a test for heteroscedasticity. Journal of Econometrics, 17(1), 107–112.
data(mtcars) m <- lm(mpg ~ wt + qsec, data = mtcars) performKoenkerTest(m, mtcars)data(mtcars) m <- lm(mpg ~ wt + qsec, data = mtcars) performKoenkerTest(m, mtcars)
Evaluates Koenker's studentized variant of the Breusch\–Pagan test (the
statistic from regressing the squared residuals on the regressors)
using streamed cross-products so that large datasets can be processed without
allocating the full auxiliary regression matrix.
performKoenkerTestStreaming(model, data, chunk_size = 10000, progress = interactive())performKoenkerTestStreaming(model, data, chunk_size = 10000, progress = interactive())
model |
A fitted stats::lm object supplying residuals and fitted values for the diagnostic. |
data |
A base::data.frame containing the variables referenced in
|
chunk_size |
Positive integer giving the number of observations processed per streaming chunk. |
progress |
Logical flag indicating whether a textual progress bar should be shown
while processing the chunks. Defaults to |
Chunks of the data contribute to the cross-product matrices for the regression of squared residuals on the model regressors. Aggregating these matrices yields the exact Koenker statistic while bounding memory usage. Sparse cross-products from Matrix are used automatically when available for large chunks.
A htest object equivalent to performKoenkerTest with metadata
recording the streaming configuration.
performKoenkerTest for the standard implementation.
data(mtcars) mod <- lm(mpg ~ wt + qsec, data = mtcars) performKoenkerTestStreaming(mod, mtcars, chunk_size = 16, progress = FALSE)data(mtcars) mod <- lm(mpg ~ wt + qsec, data = mtcars) performKoenkerTestStreaming(mod, mtcars, chunk_size = 16, progress = FALSE)
Tests equality of variances across groups using residuals from a linear model.
performLeveneTest(model, data, group)performLeveneTest(model, data, group)
model |
an object of class |
data |
data frame used to fit |
group |
name of the grouping variable. |
Absolute deviations from group means are analyzed via a one-way ANOVA. The resulting statistic has and degrees of freedom under the null of equal variances.
An object of class htest containing the F statistic, p-value and degrees of freedom.
Levene, H. (1960). Robust tests for equality of variances. In Contributions to Probability and Statistics (pp. 278–292). Stanford University Press.
Brown, M. B., & Forsythe, A. B. (1974). Robust tests for the equality of variances. Journal of the American Statistical Association, 69(346), 364–367. doi:10.1080/01621459.1974.10482955
data(mtcars) mtcars$cyl <- factor(mtcars$cyl) m <- lm(mpg ~ wt, data = mtcars) performLeveneTest(m, mtcars, "cyl")data(mtcars) mtcars$cyl <- factor(mtcars$cyl) m <- lm(mpg ~ wt, data = mtcars) performLeveneTest(m, mtcars, "cyl")
Applies the Ljung-Box test to squared residuals.
performMcLeodLiTest(model, lags = 10)performMcLeodLiTest(model, lags = 10)
model |
an object of class |
lags |
number of lags for the Ljung-Box test. |
Serial correlation in indicates conditional heteroscedasticity. The Ljung-Box statistic is compared to a chi-square distribution with the chosen number of lags.
An object of class htest containing the test statistic, p-value and degrees of freedom.
McLeod, A. I., & Li, W. K. (1983). Diagnostic checking ARMA time series models using squared-residual autocorrelations. Journal of Time Series Analysis, 4(4), 269–273.
data(mtcars) m <- lm(mpg ~ wt + qsec, data = mtcars) performMcLeodLiTest(m, lags = 10)data(mtcars) m <- lm(mpg ~ wt + qsec, data = mtcars) performMcLeodLiTest(m, lags = 10)
The Cook-Weisberg score test for non-constant error variance, the diagnostic returned by car::ncvTest().
performNCVTest(model, var_formula = NULL)performNCVTest(model, var_formula = NULL)
model |
an object of class |
var_formula |
optional one-sided formula giving the variance model, evaluated in the model frame of |
Let denote the OLS residuals and the maximum-likelihood variance estimate. The test regresses the scaled squared residuals on the variance regressors and computes half the explained sum of squares of that auxiliary regression. Under homoscedasticity and normal errors the statistic is asymptotically chi-square with degrees of freedom equal to the number of variance regressors.
With var_formula = NULL the fitted values are the sole variance regressor, matching the default of car::ncvTest() and Stata's estat hettest.
Because the divisor 2 is the null variance of under normality, the test is sensitive to non-normal errors; performKoenkerTest provides the studentized variant, which is robust to non-normal kurtosis.
An object of class htest containing the chi-square score statistic, its degrees of freedom and the p-value.
On a fit with weights the test is computed from the Pearson residuals , so it tests whether the weights are adequate; see the section on weighted fits in performKoenkerTest(), which also covers weights estimated by fitWLS().
Reproduces car::ncvTest() to within 1e-8 for both the default and the var_formula forms; see ‘tests/testthat/test-pass-a-reference.R’. Releases before 0.7.0 regressed the absolute residuals on the fitted values and reported a t statistic, which is a Glejser-type test rather than the Cook-Weisberg score test.
Cook, R. D., & Weisberg, S. (1983). Diagnostics for heteroscedasticity in regression. Biometrika, 70(1), 1–10. doi:10.1093/biomet/70.1.1
Fox, J., & Weisberg, S. (2019). An R Companion to Applied Regression (3rd ed.). SAGE.
performCookWeisbergTest, performKoenkerTest, performBPTest
data(mtcars) m <- lm(mpg ~ wt + qsec, data = mtcars) performNCVTest(m) # Score test against a specific variance model rather than the fitted values performNCVTest(m, var_formula = ~wt)data(mtcars) m <- lm(mpg ~ wt + qsec, data = mtcars) performNCVTest(m) # Score test against a specific variance model rather than the fitted values performNCVTest(m, var_formula = ~wt)
Implements O'Brien's observation-level transformed-residual test for equality of group variances.
performOBrienTest(model, data, group)performOBrienTest(model, data, group)
model |
A fitted |
data |
Data frame used to fit |
group |
Grouping variable name. |
For each residual within a group, O'Brien's transformation combines its squared deviation from the group mean with the group's sample variance and sample size. A one-way ANOVA of those transformed observations yields an approximate test. Every group must contain at least three observations.
An object of class htest containing the F statistic, numerator and denominator degrees of freedom, and p-value.
O'Brien, R. G. (1981). A simple test for variance effects in experimental designs. Psychological Bulletin, 89(3), 570–574.
set.seed(1702) n <- 25 d <- data.frame(g = factor(rep(letters[1:3], each = n)), x = rnorm(3 * n)) d$y <- 2 + d$x + rnorm(3 * n, sd = rep(c(1, 1, 1.8), each = n)) m <- lm(y ~ x, data = d) performOBrienTest(m, d, "g")set.seed(1702) n <- 25 d <- data.frame(g = factor(rep(letters[1:3], each = n)), x = rnorm(3 * n)) d$y <- 2 + d$x + rnorm(3 * n, sd = rep(c(1, 1, 1.8), each = n)) m <- lm(y ~ x, data = d) performOBrienTest(m, d, "g")
Regresses the log of squared residuals on the log of a suspected variable.
performParkTest(model, data, variable)performParkTest(model, data, variable)
model |
an object of class |
data |
data frame used to fit |
variable |
name of the suspected explanatory variable. |
The slope coefficient from regressed on is tested for zero using a t statistic. A significant coefficient indicates scale depending on .
An object of class htest containing the t statistic, p-value and degrees of freedom.
Park, R. E. (1966). Estimation with heteroscedastic error terms. Econometrica, 34(4), 888. doi:10.2307/1910108
data(mtcars) m <- lm(mpg ~ wt + qsec, data = mtcars) performParkTest(m, mtcars, "wt")data(mtcars) m <- lm(mpg ~ wt + qsec, data = mtcars) performParkTest(m, mtcars, "wt")
Checks for cross-sectional dependence in panel residuals.
performPesaranTest(model, data, id, time)performPesaranTest(model, data, id, time)
model |
an object of class |
data |
data frame used to fit |
id |
individual identifier column. |
time |
time column. |
The statistic averages pairwise correlation coefficients of the residuals and is standardized to follow a normal distribution under the null of independence.
An object of class htest.
Pesaran, M. H. (2004). General diagnostic tests for cross section dependence in panels. Cambridge Working Papers in Economics.
df <- data.frame(id = rep(1:3, each = 5), time = rep(1:5, 3), x = runif(15), y = rnorm(15)) m <- lm(y ~ x, data = df) performPesaranTest(m, df, "id", "time")df <- data.frame(id = rep(1:3, each = 5), time = rep(1:5, 3), x = runif(15), y = rnorm(15)) m <- lm(y ~ x, data = df) performPesaranTest(m, df, "id", "time")
Tests equality of regression slopes across two or more conditional quantiles using the joint Wald-type test implemented by quantreg::anova.rqs(). The procedure accounts for dependence among quantile-specific estimates from the same sample rather than treating their covariance matrices as independent.
performQuantileRegressionTest( model, data, taus = c(0.25, 0.75), se_type = c("nid", "ker"), iid = TRUE )performQuantileRegressionTest( model, data, taus = c(0.25, 0.75), se_type = c("nid", "ker"), iid = TRUE )
model |
A fitted stats::lm object describing the mean structure whose conditional quantile slopes are to be compared. |
data |
A base::data.frame containing the variables referenced in |
taus |
Numeric vector containing at least two distinct quantiles strictly between zero and one. |
se_type |
Standard-error method used by |
iid |
Logical indicating whether identical conditional densities are assumed when computing the joint test. |
Under a pure location-shift model with homoskedastic errors, regression slopes are equal across quantiles. Rejection therefore provides evidence against that location-shift/homoskedastic specification. The result should not be interpreted as a universal test for every possible form of heteroscedasticity.
Weighted fits are refused, although the resampling tests accept them. On a
fit with weights the null hypothesis is that the Pearson residuals
have constant variance, which is a
statement about the regression of on
. The quantile regressions this test
fits are of on , where the errors have variance
by assumption, so their slopes differ across
quantiles even when the weights are right. Fitting them on the weighted scale
does not by itself repair that: there the conditional quantiles are the
regression plus a constant, and the constant is not a column of the weighted
regressors. Adding a column of ones would restore the location-shift form,
but that version of the test needs its own derivation and its own size
study, and has neither.
An htest object containing the F-like joint statistic, numerator and denominator degrees of freedom, p-value, fitted quantiles, and quantile-specific slope estimates.
Koenker, R., & Bassett, G. (1982). Robust tests for heteroscedasticity based on regression quantiles. Econometrica, 50(1), 43–61.
Koenker, R. (2005). Quantile Regression. Cambridge University Press.
if (requireNamespace("quantreg", quietly = TRUE)) { # The test needs at least 40 observations, so mtcars (32) is too small. model <- lm(stations ~ mag + depth, data = quakes) performQuantileRegressionTest(model, quakes) }if (requireNamespace("quantreg", quietly = TRUE)) { # The test needs at least 40 observations, so mtcars (32) is too small. model <- lm(stations ~ mag + depth, data = quakes) performQuantileRegressionTest(model, quakes) }
Performs a non-parametric permutation test based on the rank correlation between absolute residuals and a chosen ordering variable. Significant correlations imply systematic changes in residual spread.
performRankPermutationTest( model, data, order_by = NULL, B = 999, progress = interactive() )performRankPermutationTest( model, data, order_by = NULL, B = 999, progress = interactive() )
model |
A fitted stats::lm object describing the mean structure whose residual variance is to be assessed. |
data |
A base::data.frame (or compatible object) containing the
variables referenced in |
order_by |
Optional name of a predictor variable used to rank the observations. Defaults to the first non-intercept term in the model matrix. |
B |
Number of permutation replications used to approximate the null distribution. |
progress |
Logical toggle for progress reporting during permutations. |
An htest object containing the observed Spearman
correlation and a permutation-based p-value.
Hollander, M., Wolfe, D. A., & Chicken, E. (2013). Nonparametric Statistical Methods (3rd ed.). Wiley.
data(mtcars) model <- lm(mpg ~ wt + hp, data = mtcars) set.seed(42) performRankPermutationTest(model, mtcars, B = 199, progress = FALSE)data(mtcars) model <- lm(mpg ~ wt + hp, data = mtcars) set.seed(42) performRankPermutationTest(model, mtcars, B = 199, progress = FALSE)
Adds powers of the fitted values and performs an F-test to check for neglected nonlinearity.
performRESETTest(model, power = 2:3)performRESETTest(model, power = 2:3)
model |
A fitted |
power |
Numeric vector of powers to include. |
On a fit with weights the augmented model is fitted by weighted least squares and both residual sums of squares are weighted. Releases before 0.12.0 refitted the augmented model without the weights, so the two models were not nested.
An object of class htest.
data(mtcars) m <- lm(mpg ~ wt + qsec, data = mtcars) performRESETTest(m)data(mtcars) m <- lm(mpg ~ wt + qsec, data = mtcars) performRESETTest(m)
Computes correlations between absolute residuals and selected variables.
performScatterDiagnostic(model, data, vars)performScatterDiagnostic(model, data, vars)
model |
an object of class |
data |
data frame used to fit |
vars |
character vector of variable names. |
High correlations suggest increasing spread with the explanatory variables and motivate variance-stabilizing transformations.
A named numeric vector of correlations.
Cleveland, W. S. (1979). Robust locally weighted regression and smoothing scatterplots. Journal of the American Statistical Association, 74(368), 829–836.
data(mtcars) m <- lm(mpg ~ wt + qsec, data = mtcars) performScatterDiagnostic(m, mtcars, c("wt", "qsec"))data(mtcars) m <- lm(mpg ~ wt + qsec, data = mtcars) performScatterDiagnostic(m, mtcars, c("wt", "qsec"))
Evaluates spatial clustering in squared residuals using Moran's I with a permutation reference distribution. Significant positive autocorrelation in the squared residuals is evidence of spatially varying variance.
performSpatialHeteroTest( model, data, listw, permutations = 499, zero.policy = NULL )performSpatialHeteroTest( model, data, listw, permutations = 499, zero.policy = NULL )
model |
A fitted stats::lm object describing the mean structure whose residual variance is to be assessed. |
data |
A base::data.frame (or compatible object) containing the
variables referenced in |
listw |
Spatial weights in |
permutations |
Number of Monte Carlo permutations used to compute the reference distribution. |
zero.policy |
Logical flag forwarded to the spatial diagnostic to permit islands with no neighbours. |
An htest result with Moran's I statistic applied to
squared residuals.
Anselin, L. (1988). Spatial Econometrics: Methods and Models. Kluwer.
Bivand, R. S., Pebesma, E., & Gómez-Rubio, V. (2013). Applied Spatial Data Analysis with R (2nd ed.). Springer.
if (requireNamespace("spdep", quietly = TRUE)) { data(mtcars) coords <- cbind(runif(nrow(mtcars)), runif(nrow(mtcars))) nb <- spdep::knn2nb(spdep::knearneigh(coords, k = 4)) lw <- spdep::nb2listw(nb) model <- lm(mpg ~ wt + hp, data = mtcars) performSpatialHeteroTest(model, mtcars, listw = lw, permutations = 199) }if (requireNamespace("spdep", quietly = TRUE)) { data(mtcars) coords <- cbind(runif(nrow(mtcars)), runif(nrow(mtcars))) nb <- spdep::knn2nb(spdep::knearneigh(coords, k = 4)) lw <- spdep::nb2listw(nb) model <- lm(mpg ~ wt + hp, data = mtcars) performSpatialHeteroTest(model, mtcars, listw = lw, permutations = 199) }
Computes Spearman's rho between absolute residuals and fitted values.
performSpearmanTest(model)performSpearmanTest(model)
model |
an object of class |
The squared rank correlation coefficient times the sample size minus 1 approximates a chi-square distribution with one degree of freedom.
An object of class htest containing the test statistic, p-value, degrees of freedom and rho.
Spearman, C. (1904). The proof and measurement of association between two things. American Journal of Psychology, 15(1), 72–101.
data(mtcars) m <- lm(mpg ~ wt + qsec, data = mtcars) performSpearmanTest(m)data(mtcars) m <- lm(mpg ~ wt + qsec, data = mtcars) performSpearmanTest(m)
Tests the slope of log(|residuals|) on log(fitted).
performSpreadLevelTest(model)performSpreadLevelTest(model)
model |
an object of class |
A slope near 0 indicates constant variance. A significant slope suggests a power transformation may stabilize the spread.
An object of class htest.
Cleveland, W. S. (1979). Robust locally weighted regression and smoothing scatterplots. Journal of the American Statistical Association, 74(368), 829–836.
data(mtcars) m <- lm(mpg ~ wt + qsec, data = mtcars) performSpreadLevelTest(m)data(mtcars) m <- lm(mpg ~ wt + qsec, data = mtcars) performSpreadLevelTest(m)
Computes Koenker's (1981) studentized form of the Breusch–Pagan Lagrange
multiplier statistic, from the regression of the squared
residuals on the regressors. The classical Breusch–Pagan statistic assumes
normal errors and this one does not: in the simulations of
inst/validation/ it holds its level under errors, where the
classical statistic rejects far too often.
performStudentizedBPTest(model, data)performStudentizedBPTest(model, data)
model |
A fitted stats::lm object providing the residuals and design matrix for the auxiliary regression. |
data |
A base::data.frame containing the variables used to fit
|
Following Koenker (1981) and the implementation in
lmtest::bptest(), the procedure fits an auxiliary
regression of on the regressors from the
original model (including the intercept), where denotes the
residuals and the mean of their
squares. With the fitted values of that regression, the
statistic is
its . Under homoskedasticity it is asymptotically chi-squared with
degrees of freedom equal to the number of regressors beyond the intercept,
whether or not the errors are normal. On a weighted fit is the Pearson
residual times the raw residual and the auxiliary
regression is unweighted; see the section on weighted fits in
performKoenkerTest(). This departs from lmtest::bptest(), which keeps the
raw residuals and weights the auxiliary regression. The implementation
shares the validation
helpers used across the package to ensure that: (i) the model and data satisfy
minimum sample-size thresholds via rvalidateModelInputs() and
rvalidateDataInputs(), (ii) missing values are handled by
rhandleMissingValues(), and (iii) the
requirements registered for this test in
rvalidateTestRequirements() are met.
An object of class htest reporting the chi-squared statistic
and p-value for the null hypothesis of constant error variance.
Koenker, R. (1981). A note on studentizing a test for heteroscedasticity. Journal of Econometrics, 17(1), 107–112. doi:10.1016/0304-4076(81)90062-2
Davidson, R., & MacKinnon, J. G. (2004). Econometric Theory and Methods.
Oxford University Press. Section 7.5 derives the test as from
the regression of the squared residuals on the variance regressors.
performBPTest() for the classical LM statistic, which assumes normal
errors, and performKoenkerTest(), which computes the same studentized
statistic on the squared residuals. The robust workflow in
performBPTestRobust() augments the studentized statistic with bootstrap
diagnostics.
data(mtcars) mod <- lm(mpg ~ wt + qsec, data = mtcars) performStudentizedBPTest(mod, mtcars) # Detect heteroscedasticity driven by a single regressor set.seed(321) x <- runif(180) y <- 5 - 1.5 * x + rnorm(180, sd = 0.4 + 0.6 * x) df <- data.frame(y, x) performStudentizedBPTest(lm(y ~ x, data = df), df)data(mtcars) mod <- lm(mpg ~ wt + qsec, data = mtcars) performStudentizedBPTest(mod, mtcars) # Detect heteroscedasticity driven by a single regressor set.seed(321) x <- runif(180) y <- 5 - 1.5 * x + rnorm(180, sd = 0.4 + 0.6 * x) df <- data.frame(y, x) performStudentizedBPTest(lm(y ~ x, data = df), df)
Detects monotonic changes in variance when observations can be meaningfully ordered—typically by time or another covariate—using the cumulative weighting scheme proposed by Szroeter (1978).
performSzroeterTest(model, data, order_by, alternative = c("greater", "two.sided", "less"))performSzroeterTest(model, data, order_by, alternative = c("greater", "two.sided", "less"))
model |
A fitted stats::lm object representing the mean equation under study. |
data |
A base::data.frame (or compatible tibble) containing the
variables used to fit |
order_by |
Character scalar naming the column that defines the ordering of observations prior to computing the statistic. The column must be numeric or coercible to an orderable vector. |
alternative |
Character scalar specifying the alternative hypothesis:
|
After ordering the residuals by order_by, the test forms
the rank-weighted average of the squared residuals
which is Szroeter's (1978) class of statistics evaluated at the canonical
weights . Under homoskedasticity is centred on the mean
rank with variance , so
is asymptotically standard normal. Variance that grows with order_by shifts
weight onto the high ranks and drives upwards.
The implementation relies on the package validation helpers to align the supplied data with the model residuals, check that the ordering variable is present, and ensure sufficient sample size and variability in the squared residuals.
Ties in order_by keep the order of the rows the model was fitted to.
Unless the rows were sorted by the response, that order does not depend on
the residuals, so the test keeps its level under the null hypothesis; but
with a discrete ordering variable the statistic depends on the order of the
rows.
runHeteroTests(tests = "szroeter"), and anything else that runs the
registered diagnostic, orders the observations by the fitted values of
model, so its alternative is variance that rises with the mean. With a
single regressor that is the order of the regressor when its slope is
positive and the reverse order when it is negative. The fitted values are
computed from the coefficients, so observations with the same regressors
tie exactly, as they do under a factor or a binary regressor, and the ties
are broken as above.
An object of class htest reporting Szroeter's
standardised statistic Q, the sample size, the underlying rank-weighted
statistic h in estimate, and the p-value from the asymptotic normal
reference distribution.
The statistic and its null variance are checked against an independent
reconstruction of Szroeter (1978) in
‘tests/testthat/test-pass-a-reference.R’. Releases before 0.7.0 divided
the centred statistic by a further , shrinking by a
factor of roughly and leaving the test with essentially no
power against any alternative; see ‘NEWS.md’.
Szroeter, J. (1978). A class of parametric tests for heteroscedasticity in linear econometric models. Econometrica, 46(6), 1311–1327. doi:10.2307/1913833
Godfrey, L. G. (1988). Misspecification Tests in Econometrics. Cambridge University Press. Section 5.4 outlines the Szroeter test.
performKoenkerTest() for the regressor-based alternative and
performGQTest() for split-sample diagnostics on ordered data.
data(mtcars) mod <- lm(mpg ~ wt + qsec, data = mtcars) performSzroeterTest(mod, mtcars, order_by = "wt") # Detect ordered heteroscedasticity in simulated data with variance increasing # in an index variable set.seed(404) n <- 150 x <- sort(runif(n)) y <- 2 + 0.5 * x + rnorm(n, sd = 0.4 + 0.8 * x) df <- data.frame(y, x) performSzroeterTest(lm(y ~ x, data = df), df, order_by = "x") # Two-sided version when the direction of the change is not known in advance performSzroeterTest(mod, mtcars, order_by = "wt", alternative = "two.sided")data(mtcars) mod <- lm(mpg ~ wt + qsec, data = mtcars) performSzroeterTest(mod, mtcars, order_by = "wt") # Detect ordered heteroscedasticity in simulated data with variance increasing # in an index variable set.seed(404) n <- 150 x <- sort(runif(n)) y <- 2 + 0.5 * x + rnorm(n, sd = 0.4 + 0.8 * x) df <- data.frame(y, x) performSzroeterTest(lm(y ~ x, data = df), df, order_by = "x") # Two-sided version when the direction of the change is not known in advance performSzroeterTest(mod, mtcars, order_by = "wt", alternative = "two.sided")
Tests whether the error variance follows a stated parametric function of
stated variables, . Every other test in the
package has constant variance as its null hypothesis, so it can say that the
variance moves with some variables but not whether an exponential or a power
function of them describes it. Here the variance function is the null
hypothesis, and rejecting it means that the chosen shape is inadequate.
performVarianceFormTest( model, data = NULL, var_formula = NULL, form = c("exponential", "power"), against = "squares" )performVarianceFormTest( model, data = NULL, var_formula = NULL, form = c("exponential", "power"), against = "squares" )
model |
A fitted stats::lm object for the mean equation, or the result
of |
data |
Optional base::data.frame holding the variables named in
|
var_formula |
One-sided formula naming the variance regressors
|
form |
Character scalar giving the variance function under the null:
|
against |
The terms the variance function is tested against. The
default, |
The procedure has three steps.
The variance function is fitted to the residuals of model and the
model is refitted by weighted least squares, exactly as fitWLS() does.
The squared standardized residuals
of the weighted fit are
formed. If the variance function is right their mean does not depend on
anything.
is regressed on a constant, on
,
and on the added terms . The statistic is the F test that the
coefficients on are zero.
For the exponential form is , and for the power form it
is . The regression is the score direction of the variance
function extended by the added terms, so the test is a studentized Lagrange
multiplier test of the stated form against that extension.
Step 3 keeps in the regression for a reason. Estimating
fits the variance along , so those directions say
little about the form: a Breusch–Pagan or Koenker test of the weighted fit
on the same variance regressors rejects a wrong form about as often as the
right one. The information is in the terms outside the fitted variance
function. Conditioning on is also what makes the null
distribution free of the error in to first order, which is
the regression-based construction of Wooldridge (1990, 1991).
An object of class htest with the F statistic, its numerator
and denominator degrees of freedom, and the p-value for the null hypothesis
that the variance function is correctly specified. estimate holds the
fitted coefficients of the variance function: slopes of the log-variance
for the exponential form and exponents for the power form. The element
variance_function records the form, the variance regressors and the
added terms that entered the test.
A rejection says that the added terms move the variance beyond what the
stated function allows. A non-rejection says only that those terms do not;
it does not establish the form. Two functions that are close over the
observed range of cannot be told apart, and the test will then
accept both: a variance that is linear in a regressor is accepted as
exponential or as a power when the regressor varies over a short range.
Running the test for several forms is a comparison of fits, and choosing
the form with the largest p-value is not a test.
The test judges the shape, not the fitted coefficients. Because it
conditions on , it does not respond to weights that are off along
the variance regressors themselves. A test of constant variance on the
weighted fit is sensitive to that, with the reservations about its level
described under weighted fits in performKoenkerTest().
The F reference distribution assumes that the standardized errors have a constant fourth moment, the assumption behind the Koenker test. It does not assume normality.
With variance regressors the default adds up to
terms. When that is large relative to the sample, name
the variance regressors with var_formula or the added terms with
against.
No reference implementation exists, so the statistic is checked against a
reconstruction from its definition to 1e-8
(tests/testthat/test-variance-form.R) and by simulation. Over 24 designs
in which the form under test was right (both forms, constant and
heteroscedastic variances, 50 to 400 observations, Gaussian and
errors, 5000 replications each) the rejection rate at the 5%
level ran from 4.2% to 5.7%. Power against a log-variance that is
quadratic in a regressor was 98% at 150 observations. Against the other
log-linear form it was 22% at 150 observations and 74% at 400. See
inst/validation/README.md.
Wooldridge, J. M. (1990). A unified approach to robust, regression-based specification tests. Econometric Theory, 6(1), 17–43. doi:10.1017/S0266466600004898
Wooldridge, J. M. (1991). On the application of robust, regression-based diagnostics to models of conditional means and conditional variances. Journal of Econometrics, 47(1), 5–46. doi:10.1016/0304-4076(91)90076-P
Harvey, A. C. (1976). Estimating regression models with multiplicative heteroscedasticity. Econometrica, 44(3), 461–465. doi:10.2307/1913974
Koenker, R. (1981). A note on studentizing a test for heteroscedasticity. Journal of Econometrics, 17(1), 107–112. doi:10.1016/0304-4076(81)90062-2
Carroll, R. J., & Ruppert, D. (1988). Transformation and Weighting in Regression. Chapman & Hall. Chapter 3 treats the estimation and checking of variance functions.
fitWLS() fits the variance functions tested here. performHarveyTest()
and performParkTest() test constant variance against the exponential and
the power form respectively.
# Standard deviation proportional to x, so the variance is a power of x set.seed(2026) n <- 300 sim <- data.frame(x = runif(n, 1, 5)) sim$y <- 1 + 2 * sim$x + sim$x * rnorm(n) mod <- lm(y ~ x, data = sim) # The power form is the true one; estimate is the fitted exponent performVarianceFormTest(mod, form = "power") # The exponential form in x is not performVarianceFormTest(mod, form = "exponential") # Test the variance function of a weighted fit directly wls <- fitWLS(mod, form = "power") performVarianceFormTest(wls) # Test a variance function against one particular added term performVarianceFormTest(mod, form = "exponential", against = ~ log(x))# Standard deviation proportional to x, so the variance is a power of x set.seed(2026) n <- 300 sim <- data.frame(x = runif(n, 1, 5)) sim$y <- 1 + 2 * sim$x + sim$x * rnorm(n) mod <- lm(y ~ x, data = sim) # The power form is the true one; estimate is the fitted exponent performVarianceFormTest(mod, form = "power") # The exponential form in x is not performVarianceFormTest(mod, form = "exponential") # Test the variance function of a weighted fit directly wls <- fitWLS(mod, form = "power") performVarianceFormTest(wls) # Test a variance function against one particular added term performVarianceFormTest(mod, form = "exponential", against = ~ log(x))
Compute variance inflation factors for assessing multicollinearity. Each VIF is the corresponding diagonal element of the inverse correlation matrix of the design, so the computation works for models containing factors (each contrast column receives its own VIF).
performVIFDiagnostic(model)performVIFDiagnostic(model)
model |
A fitted |
A named numeric vector of VIF values, one per design-matrix column
(excluding the intercept). Perfectly collinear columns are reported as Inf.
data(mtcars) m <- lm(mpg ~ wt + qsec, data = mtcars) performVIFDiagnostic(m)data(mtcars) m <- lm(mpg ~ wt + qsec, data = mtcars) performVIFDiagnostic(m)
Implements White's test on a fitted linear model.
performWhiteTest(model, data, cross_products = TRUE, max_interactions = 10)performWhiteTest(model, data, cross_products = TRUE, max_interactions = 10)
model |
an object of class |
data |
Data frame used to fit |
cross_products |
Logical. Include cross-product terms in the auxiliary regression? |
max_interactions |
Maximum number of cross-product terms admitted to the auxiliary regression. Guards the auxiliary design against growing quadratically with the number of regressors. |
An auxiliary regression of on all regressors, their squares and cross-products produces . The statistic follows a chi-square distribution with degrees of freedom equal to the number of regressors in the auxiliary model.
An object of class htest containing the test statistic, p-value and degrees of freedom.
On a fit with weights the test is computed from the Pearson residuals , so it tests whether the weights are adequate; see the section on weighted fits in performKoenkerTest(), which also covers weights estimated by fitWLS().
White, H. (1980). A heteroskedasticity-consistent covariance matrix estimator and a direct test for heteroskedasticity. Econometrica, 48(4), 817–838. doi:10.2307/1912934
Greene, W. H. (2018). Econometric Analysis (8th ed.). Pearson.
data(mtcars) m <- lm(mpg ~ wt + qsec, data = mtcars) performWhiteTest(m, mtcars)data(mtcars) m <- lm(mpg ~ wt + qsec, data = mtcars) performWhiteTest(m, mtcars)
Approximates the finite-sample distribution of White's LM statistic by resampling the fitted residuals, refitting the model, and recalculating the test statistic across many bootstrap replications.
performWhiteTestBootstrap(model, data, B = 1000, parallel = FALSE)performWhiteTestBootstrap(model, data, B = 1000, parallel = FALSE)
model |
A fitted stats::lm object representing the mean specification to be diagnosed. |
data |
A base::data.frame (or object coercible to one) containing the
variables referenced by |
B |
Integer scalar giving the number of bootstrap replications. Larger values yield smoother p-value estimates at the cost of additional runtime. |
parallel |
Logical scalar; if |
For a fitted model , the algorithm proceeds as
follows:
Compute White's LM statistic from the auxiliary regression
on squares and cross-products of the regressors.
Generate bootstrap samples by resampling the centred residuals
with replacement, forming .
Refit the model to each bootstrap sample and recompute White's
statistic using the same auxiliary specification.
Estimate the bootstrap p-value as
,
where runs over the replicates whose
statistic is finite, so the p-value is never zero.
The bootstrap distribution offers improved size control for moderate sample
sizes or high-dimensional designs where the chi-squared approximation may be
inaccurate. When parallel = TRUE the resampling step exploits available CPU
cores to reduce computation time.
A htest object reporting both the asymptotic White statistic
and its bootstrap p-value. The returned object also stores the simulated test
statistics in boot_statistics for further inspection.
A fit with weights is ordinary least squares on
and ,
whose errors have constant variance under the null hypothesis, and the
bootstrap is carried out in that regression. What is resampled is its
residuals, the Pearson residuals .
When the model has an intercept they are centred, as the residuals of an
unweighted fit with an intercept are, because the weighted regression has
no constant column. Each draw is divided by to
return it to the scale of the observation it is added to, and each
replicate is refitted with the weights, so performWhiteTest() computes
its statistic from the Pearson residuals as it does for the fit supplied.
With equal weights the result is that of the unweighted fit.
Weighted or not, each replicate is refitted with an offset the model was
given as an argument, lm(..., offset = o); an offset written in the
formula, offset(o), is evaluated again from the data of the replicate.
The weights are held fixed in every replicate. When they were estimated
from the same data, as by fitWLS(), the replicates leave that estimation
out. In inst/validation/weighted-fits-size.R, on data whose standard
deviation is , with the variance function
correctly specified, normal errors, 150 observations and B = 499, the
rejection rate at the 5% level was 0.064. In the same design with the true
weights it was 0.054, and with the weights estimated again in each
replicate, which this function does not do, 0.042. The section on weighted
fits in performWildBootstrapTest() has the larger error of Koenker's
statistic.
Efron, B., & Tibshirani, R. J. (1993). An Introduction to the Bootstrap. Chapman & Hall/CRC.
Davidson, R., & MacKinnon, J. G. (2006). The power of bootstrap and asymptotic tests. Journal of Econometrics, 133(2), 421–441. doi:10.1016/j.jeconom.2005.02.002
performWhiteTest() for the classical statistic and
performWhiteTestRobust() for enriched diagnostics.
# The bootstrap needs at least 50 observations, so mtcars (32) is too small. set.seed(42) n <- 120 sim <- data.frame(x = runif(n, 1, 5)) sim$y <- 1 + 2 * sim$x + rnorm(n, sd = 0.3 + 0.6 * sim$x) mod <- lm(y ~ x, data = sim) performWhiteTestBootstrap(mod, sim, B = 199) # More replications give a smoother p-value estimate performWhiteTestBootstrap(mod, sim, B = 499) # parallel = TRUE forks parallel::detectCores() - 1 workers, which Windows # does not support. The call runs only where that is at most two workers, # the most R CMD check --as-cran allows. if (.Platform$OS.type != "windows" && isTRUE(parallel::detectCores() <= 3L)) { performWhiteTestBootstrap(mod, sim, B = 199, parallel = TRUE) }# The bootstrap needs at least 50 observations, so mtcars (32) is too small. set.seed(42) n <- 120 sim <- data.frame(x = runif(n, 1, 5)) sim$y <- 1 + 2 * sim$x + rnorm(n, sd = 0.3 + 0.6 * sim$x) mod <- lm(y ~ x, data = sim) performWhiteTestBootstrap(mod, sim, B = 199) # More replications give a smoother p-value estimate performWhiteTestBootstrap(mod, sim, B = 499) # parallel = TRUE forks parallel::detectCores() - 1 workers, which Windows # does not support. The call runs only where that is at most two workers, # the most R CMD check --as-cran allows. if (.Platform$OS.type != "windows" && isTRUE(parallel::detectCores() <= 3L)) { performWhiteTestBootstrap(mod, sim, B = 199, parallel = TRUE) }
Extends performWhiteTest() with optional bootstrap resampling, confidence
intervals, effect size reporting, and power analysis.
performWhiteTestRobust( model, data, method = c("standard", "reduced"), bootstrap = FALSE, B = 1000, ci_level = 0.95, parallel = FALSE )performWhiteTestRobust( model, data, method = c("standard", "reduced"), bootstrap = FALSE, B = 1000, ci_level = 0.95, parallel = FALSE )
model |
A fitted stats::lm object representing the mean specification to be diagnosed. |
data |
A base::data.frame (or object coercible to one) containing the
variables referenced by |
method |
Character string selecting the auxiliary specification. "standard" retains squares and cross-products, while "reduced" excludes cross-products for high-dimensional designs. |
bootstrap |
Logical, compute bootstrap diagnostics for the statistic and p-value? |
B |
Number of bootstrap replications when |
ci_level |
Confidence level for reported intervals. |
parallel |
Logical, allow parallel bootstrap evaluation when the
|
Provides enriched inference around the White test by combining bootstrap
resampling (Efron & Tibshirani, 1993) with asymptotic approximations. The
robust_details element summarises interval estimates, effect sizes, and power
calculations to aid decision-making.
An object of class htest augmented with a
robust_details list containing bootstrap, effect size, and power
information.
White, H. (1980). A heteroskedasticity-consistent covariance matrix estimator and a direct test for heteroscedasticity. Econometrica, 48(4), 817–838.
Efron, B., & Tibshirani, R. J. (1993). An Introduction to the Bootstrap. Chapman & Hall.
performWhiteTest() for the base statistic and
performWhiteTestBootstrap() for a lighter-weight resampling option.
data(mtcars) mod <- lm(mpg ~ wt + qsec, data = mtcars) performWhiteTestRobust(mod, mtcars, bootstrap = TRUE, B = 200)data(mtcars) mod <- lm(mpg ~ wt + qsec, data = mtcars) performWhiteTestRobust(mod, mtcars, bootstrap = TRUE, B = 200)
Computes White's statistic via chunked cross-products rather than fitting the full auxiliary regression in memory. This streaming approach allows the test to scale to datasets that would otherwise exhaust available RAM.
performWhiteTestStreaming( model, data, chunk_size = 10000, cross_products = TRUE, max_interactions = 10, progress = interactive() )performWhiteTestStreaming( model, data, chunk_size = 10000, cross_products = TRUE, max_interactions = 10, progress = interactive() )
model |
A fitted stats::lm object representing the mean specification to be diagnosed. |
data |
A base::data.frame (or object coercible to one) containing the
variables referenced by |
chunk_size |
Positive integer specifying the number of observations per chunk. Smaller values reduce memory usage at the expense of additional iteration overhead. |
cross_products |
Logical scalar indicating whether to include all
pairwise cross-products of the regressors in the auxiliary regression.
Defaults to |
max_interactions |
Single positive integer giving the maximum number of
original predictors for which cross-products are generated. When the number
of regressors exceeds this threshold, cross-products are dropped to avoid
explosive growth in columns. Defaults to |
progress |
Logical flag indicating whether a progress bar should be
displayed while streaming the data. Defaults to |
The streaming implementation iteratively builds the cross-product matrices
required for the auxiliary regression without materialising the full design
matrix. Each chunk contributes to , , and summary statistics
for the response. The final statistic is then computed exactly as
in the standard White test, ensuring numerical equivalence while dramatically
reducing peak memory usage. When Matrix is installed, sparse cross-products
are leveraged automatically for large chunks.
A htest object containing the chi-squared statistic, p-value,
and metadata about the chunked computation.
White, H. (1980). A heteroskedasticity-consistent covariance matrix estimator and a direct test for heteroscedasticity. Econometrica, 48(4), 817–838.
performWhiteTest() for the exact computation and performWhiteTestRobust() for
enhanced reporting.
data(mtcars) performWhiteTestStreaming(lm(mpg ~ wt + qsec, data = mtcars), mtcars, chunk_size = 16)data(mtcars) performWhiteTestStreaming(lm(mpg ~ wt + qsec, data = mtcars), mtcars, chunk_size = 16)
Calibrates the Breusch-Pagan Lagrange multiplier statistic with a
null-imposed wild bootstrap, providing a p-value that is accurate in small
samples and under non-normal errors without relying on the asymptotic
approximation.
performWildBootstrapTest( model, data, B = 499, distribution = c("rademacher", "mammen"), progress = interactive() )performWildBootstrapTest( model, data, B = 499, distribution = c("rademacher", "mammen"), progress = interactive() )
model |
A fitted stats::lm object describing the mean structure whose residual variance is to be assessed. |
data |
A base::data.frame (or compatible object) containing the
variables referenced in |
B |
Integer number of bootstrap replications. Defaults to |
distribution |
Multiplier distribution used for the wild perturbation. Supported options are "rademacher" and "mammen". |
progress |
Logical flag controlling whether progress should be reported when running the bootstrap loop. |
The observed statistic is the usual from the auxiliary regression of
the squared residuals on the regressors. The bootstrap reference distribution,
however, must be generated under the homoscedastic null — otherwise it
inherits the heteroscedasticity the test is looking for and the procedure loses
all power. Each bootstrap sample is therefore built from leverage-standardised,
mean-centred residuals (which have a common
variance under ) resampled i.i.d. and perturbed by a wild multiplier
, so that . The statistic is recomputed
on each refit and the p-value is . Under
this controls size even for heavy-tailed errors; under the alternative
the observed statistic is extreme relative to the homoscedastic reference, giving
power.
Each replicate is refitted on the design matrix of the fit, with its
offset, whether that was given as an argument or written in the formula.
The formula is not evaluated again, so a transformed regressor such as
log(x), or a transformed response, is refitted on the scale of the fit.
An object of class htest containing the observed
Breusch-Pagan statistic, bootstrap p-value, and additional details under the
bootstrap element.
A fit with weights is ordinary least squares on
and ,
whose errors have constant variance under the null hypothesis, and the
bootstrap works in that regression. The statistic is computed from its
residuals, the Pearson residuals , with
the auxiliary regressors on their original scale; the residuals that are
resampled are the Pearson residuals divided by
, with the leverages of that
regression, and centred; and each replicate refits it. With equal weights
the result is that of the unweighted fit.
The weights are held fixed in every replicate. When they were estimated
from the same data, as by fitWLS(), the replicates leave that estimation
out, and the test inherits the error of the tests that take the weights as
known. In inst/validation/weighted-fits-size.R, on data whose standard
deviation is , with the variance function
correctly specified, normal errors and B = 499, its rejection rate at the
5% level was 0.086 with 150 observations and 0.105 with 600. In the same
design with the true weights it was 0.054 and 0.048, and with the weights
estimated again in each replicate, which this function does not do, 0.060
and 0.051. performVarianceFormTest() allows for the estimation.
Davidson, R., & Flachaire, E. (2008). The wild bootstrap, tamed at last. Journal of Econometrics, 146(1), 162–169.
Godfrey, L. G. (2006). Tests for regression models with heteroskedasticity of unknown form. Computational Statistics & Data Analysis, 50(10), 2715–2733.
Wu, C. F. J. (1986). Jackknife, bootstrap and other resampling methods in regression analysis. The Annals of Statistics, 14(4), 1261–1295.
data(mtcars) model <- lm(mpg ~ wt + qsec, data = mtcars) if (interactive()) { set.seed(123) performWildBootstrapTest(model, mtcars, B = 199, progress = FALSE) }data(mtcars) model <- lm(mpg ~ wt + qsec, data = mtcars) if (interactive()) { set.seed(123) performWildBootstrapTest(model, mtcars, B = 199, progress = FALSE) }
Produce basic residual diagnostic plots.
## S3 method for class 'HeteroDiagnostic' plot(x, plots = c("residuals_fitted", "spread_level", "density", "qq", "bubble_variance"), ...)## S3 method for class 'HeteroDiagnostic' plot(x, plots = c("residuals_fitted", "spread_level", "density", "qq", "bubble_variance"), ...)
x |
A |
plots |
Character vector selecting which diagnostic panels to draw. |
... |
Further arguments passed to the underlying plotting routines. |
List of ggplot objects.
Plot method for power analysis results
## S3 method for class 'power_analysis' plot(x, ...)## S3 method for class 'power_analysis' plot(x, ...)
x |
Object returned by |
... |
Further arguments passed to the underlying plotting routines. |
Draws the residuals of two models against their fitted values in two panels, side by side, to show what a remediation method (a weighted fit, a transformation) did to the spread.
plotBeforeAfter(original, remedied)plotBeforeAfter(original, remedied)
original |
The original |
remedied |
The model fitted after remediation. |
A weighted fit is shown through its Pearson residuals ,
so the plot shows whether the weighting flattened the spread. Its raw
residuals would look as heteroscedastic as the original ones however good
the weights were.
Each panel has its own axes. Weighted residuals and the residuals of a transformed response are not in the units of the original ones, and on a common axis one of the two panels could be squeezed flat. The panels are there to compare the shape of the two clouds, not their size.
A ggplot object with one panel per model. Its data have the
columns fitted, resid, model ("original" or "remedied") and
panel.
Up to 0.12.0 the two sets of residuals were overlaid in one panel and told apart by colour.
data(mtcars) m1 <- lm(mpg ~ wt, data = mtcars) m2 <- fitWLS(m1) plotBeforeAfter(m1, m2)data(mtcars) m1 <- lm(mpg ~ wt, data = mtcars) m2 <- fitWLS(m1) plotBeforeAfter(m1, m2)
Displays residual magnitude against a predictor with bubble size
proportional to |residual|.
plotBubbleVariance(model, variable = NULL)plotBubbleVariance(model, variable = NULL)
model |
A fitted model of class |
variable |
Optional name of a covariate from the model to plot against. |
A ggplot object.
data(mtcars) m <- lm(mpg ~ wt + qsec, data = mtcars) plotBubbleVariance(m, "wt")data(mtcars) m <- lm(mpg ~ wt + qsec, data = mtcars) plotBubbleVariance(m, "wt")
This convenience wrapper returns residual-vs-fitted and spread-level plots to help visually assess heteroscedastic patterns.
plotDiagnosticSuite(model)plotDiagnosticSuite(model)
model |
A fitted model of class |
A list with elements residuals_fitted and spread_level, each a
ggplot object.
data(mtcars) m <- lm(mpg ~ wt + qsec, data = mtcars) plots <- plotDiagnosticSuite(m) plots$residuals_fitteddata(mtcars) m <- lm(mpg ~ wt + qsec, data = mtcars) plots <- plotDiagnosticSuite(m) plots$residuals_fitted
Returns a list of improved diagnostic plots with statistical overlays.
plotDiagnosticSuiteEnhanced(model)plotDiagnosticSuiteEnhanced(model)
model |
A fitted model of class |
A list of ggplot objects.
Shows the distribution of residuals with a kernel density estimate.
plotResidualDensity(model)plotResidualDensity(model)
model |
A fitted model of class |
A ggplot object.
data(mtcars) m <- lm(mpg ~ wt + qsec, data = mtcars) plotResidualDensity(m)data(mtcars) m <- lm(mpg ~ wt + qsec, data = mtcars) plotResidualDensity(m)
Visualises departure from normality using a QQ plot.
plotResidualQQ(model)plotResidualQQ(model)
model |
A fitted model of class |
A ggplot object.
data(mtcars) m <- lm(mpg ~ wt + qsec, data = mtcars) plotResidualQQ(m)data(mtcars) m <- lm(mpg ~ wt + qsec, data = mtcars) plotResidualQQ(m)
Generates a simple scatter plot of residuals against fitted values from a linear model. A horizontal reference line at zero is added.
plotResidualsFitted(model)plotResidualsFitted(model)
model |
A fitted model of class |
For a weighted fit the Pearson residuals are plotted,
as in plot.lm(): those are the residuals that have constant variance when
the weights are right. The other residual plots in the package do the same.
A ggplot object.
data(mtcars) m <- lm(mpg ~ wt + qsec, data = mtcars) plotResidualsFitted(m)data(mtcars) m <- lm(mpg ~ wt + qsec, data = mtcars) plotResidualsFitted(m)
Highlights influential observations and includes a LOESS smooth with confidence bands.
plotResidualsFittedEnhanced(model)plotResidualsFittedEnhanced(model)
model |
A fitted model of class |
A ggplot object.
Plots the square root of the absolute residuals against fitted values. A lowess smooth is added to highlight trends.
plotSpreadLevel(model)plotSpreadLevel(model)
model |
A fitted model of class |
A ggplot object.
data(mtcars) m <- lm(mpg ~ wt + qsec, data = mtcars) plotSpreadLevel(m)data(mtcars) m <- lm(mpg ~ wt + qsec, data = mtcars) plotSpreadLevel(m)
Print method for enhanced White test results
## S3 method for class 'htest_enhanced' print(x, ...)## S3 method for class 'htest_enhanced' print(x, ...)
x |
An object of class |
... |
Further arguments passed to |
Provides a consistent wrapper around bootstrap resampling for test
statistics produced by heteroscedasticity diagnostics. The routine
refits the supplied model on each bootstrap replicate and evaluates
test_function on it, returning the bootstrap distribution, a
percentile interval, and—for null-imposed resampling—a p-value.
rbootstrap_test_statistic( test_function, model, data, B = 1000, parallel = FALSE, ci_level = 0.95, resample = c("null", "pairs"), n_cores = NULL, progress = interactive(), ... )rbootstrap_test_statistic( test_function, model, data, B = 1000, parallel = FALSE, ci_level = 0.95, resample = c("null", "pairs"), n_cores = NULL, progress = interactive(), ... )
test_function |
A function that accepts |
model |
A fitted model of class |
data |
Data frame used when fitting |
B |
Integer, number of bootstrap replications. Defaults to 1000. |
parallel |
Logical, compute replicates in parallel when possible? |
ci_level |
Confidence level for the percentile interval. |
resample |
Bootstrap strategy. |
n_cores |
Optional integer specifying the number of worker processes to
use when |
progress |
Logical flag controlling whether a textual progress bar is displayed during bootstrap replication. |
... |
Additional arguments forwarded to |
The resample argument decides what the replicates mean.
With resample = "null" (the default) the response is regenerated as
, where the are drawn with replacement from
the model's residuals after dividing by and centring.
Those data satisfy homoscedasticity by construction, so the replicates
estimate the null distribution and p_value is a test. The leverage
correction matters: OLS residuals have variance , and
resampling them unscaled under-disperses the regenerated errors, which
inflates the rejection rate.
With resample = "pairs" rows are sampled with replacement. The
replicates then follow the statistic's distribution under whatever variance
structure the data actually have, which is useful for describing its
variability but is not a null distribution: the replicates are centred on the
observed statistic, so comparing the two returns roughly 0.5 whatever the
data. Measured rejection under was 0%.
p_value is therefore NA for pairs resampling.
Neither strategy accepts a glm: each replicate is refitted with least
squares, so the family and link would be discarded and the replicates would
describe a different model from the one supplied.
A weighted lm is resampled on the scale where its null hypothesis is
constant variance, the regression of
on . Null-imposed resampling draws the
from the Pearson residuals
, divided by
with the leverages of that regression and
centred, and divides each draw by before adding
it to .
Pairs resampling draws each row with its weight. Either way each replicate
is refitted with the weights, so test_function sees a weighted fit, as it
did on the original data. The weights are held fixed; when they were
estimated from the same data, see the section on weighted fits in
performWildBootstrapTest().
Weighted or not, each replicate is refitted with an offset the model was
given as an argument, lm(..., offset = o); an offset written in the
formula, offset(o), is evaluated again from the data of the replicate.
The rows of data are matched to those of the fit by row name, so that
each row is regenerated, or drawn, with its own fitted value, weight and
offset. Rows the model was not fitted to, such as those it dropped for
missing values, are left out, for the observed statistic as for the
replicates; the rows that stay keep the order of data. data that lacks
a row the model was fitted to is refused. Data without row names of its
own, such as a tibble or a data.table, that has as many rows as the fit is
taken in the order of the fit. The model is then refitted to the rows of
data, and data is refused when that refit does not give the residuals
of the fit to a relative 1e-8: rows in another order taken by position,
values that differ from those the model was fitted to, or a variable the
formula finds outside data, which keeps the order of the fit. Pairs
resampling of a model with such a variable, for example offset(o) with
o in the environment of the formula, is refused too; give such an offset
as an argument instead.
Null-imposed resampling additionally requires the response to be a plain
variable. For log(y) ~ x the fitted values are on the log scale while
the data column holds y, so regenerating one from the other and
refitting would take the logarithm twice. That case raises an error;
resample = "pairs" resamples rows and is unaffected by it.
A list with components:
originalResult returned by test_function on the
original data.
original_statisticNumeric value of the test statistic from the original sample.
replicatesNumeric vector of bootstrap statistics.
ciPercentile interval of the bootstrap distribution of the
statistic, at ci_level. This summarises where the resampled statistic
falls; it is not a confidence interval for a parameter and carries no
coverage guarantee.
p_valueEmpirical p-value from the null-imposed replicates,
computed as ;
NA when resample = "pairs".
BRequested number of replications.
effective_samplesNumber of non-missing bootstrap replications.
callMatched call for reproducibility.
data(mtcars) model <- lm(mpg ~ wt + cyl, data = mtcars) if (interactive()) { set.seed(123) boot <- rbootstrap_test_statistic(performWhiteTest, model, mtcars, B = 100) boot$ci }data(mtcars) model <- lm(mpg ~ wt + cyl, data = mtcars) if (interactive()) { set.seed(123) boot <- rbootstrap_test_statistic(performWhiteTest, model, mtcars, B = 100) boot$ci }
Converts chi-squared statistics produced by heteroscedasticity tests into interpretable effect sizes such as Cramer's V, the phi coefficient, or an eta-squared analogue. The helper also provides qualitative magnitude descriptors and a brief interpretation string that can be surfaced to users.
rcalculateEffectSize( test_result, model, data, type = c("cramers_v", "phi", "eta_squared") )rcalculateEffectSize( test_result, model, data, type = c("cramers_v", "phi", "eta_squared") )
test_result |
Result object from a heteroscedasticity test (typically
of class |
model |
Fitted model supplied to the diagnostic. |
data |
Data frame containing the variables referenced in |
type |
Effect size metric to compute. Supported options are
|
A named list with elements effect_size, magnitude,
practical_significance, interpretation, and type.
data(mtcars) model <- lm(mpg ~ wt + cyl, data = mtcars) result <- performWhiteTest(model, mtcars) rcalculateEffectSize(result, model, mtcars)data(mtcars) model <- lm(mpg ~ wt + cyl, data = mtcars) result <- performWhiteTest(model, mtcars) rcalculateEffectSize(result, model, mtcars)
Adds a function to the diagnostics registry so it can be called by runHeteroTests.
registerDiagnostic(name, fun)registerDiagnostic(name, fun)
name |
Name of the diagnostic. |
fun |
Function taking |
Invisibly returns NULL.
listDiagnostics for the names already registered.
custom <- function(model, data) list(statistic = 0) registerDiagnostic("custom", custom)custom <- function(model, data) list(statistic = 0) registerDiagnostic("custom", custom)
Register a diagnostic plot
registerPlot(name, fun)registerPlot(name, fun)
name |
Name of the plot |
fun |
Function taking a model and returning a ggplot object |
Invisibly returns NULL.
registerPlot("custom_plot", function(model) ggplot2::ggplot())registerPlot("custom_plot", function(model) ggplot2::ggplot())
Uses the observed chi-squared statistic and effect size to approximate the achieved power of a heteroscedasticity test and to suggest an increased sample size required to attain the desired power threshold.
restimate_test_power( test_result, model, data, alpha = 0.05, target_power = 0.8, max_multiplier = 5 )restimate_test_power( test_result, model, data, alpha = 0.05, target_power = 0.8, max_multiplier = 5 )
test_result |
An object returned by |
model |
Fitted model used in the diagnostic. |
data |
Data frame supplied to the diagnostic. |
alpha |
Significance level used in the test. Defaults to 0.05. |
target_power |
Desired minimum power for the recommendation. |
max_multiplier |
Upper bound multiplier relative to the observed sample size when searching for the recommended sample size. |
A list with elements power, recommended_n, and details
containing auxiliary information (degrees of freedom, non-centrality
parameter, and a power curve over a grid of effect sizes).
Provides enhanced implementations of core heteroscedasticity diagnostics with bootstrap support, effect size calculations, and statistical power summaries. The module also exposes orchestration helpers for running the enhanced diagnostics in batch and utilities for validating results against reference implementations from other packages.
Executes one or more robust diagnostics with automatic enhancements for small samples and optional studentisation.
rrunAdvancedDiagnostics( model, data, tests = "all", auto_enhance = TRUE, bootstrap_B = 500, parallel = FALSE, ci_level = 0.95 )rrunAdvancedDiagnostics( model, data, tests = "all", auto_enhance = TRUE, bootstrap_B = 500, parallel = FALSE, ci_level = 0.95 )
model |
A fitted stats::lm object representing the mean specification to be diagnosed. |
data |
A base::data.frame (or object coercible to one) containing the
variables referenced by |
tests |
Character vector of tests to run. Use "all" (default) to
run the White and Breusch-Pagan diagnostics, or supply a subset such
as |
auto_enhance |
Logical, enable automatic bootstrap for small samples (n < 50) and studentization for Breusch-Pagan. |
bootstrap_B |
Number of bootstrap replications used when automatic enhancement triggers bootstrap. |
parallel |
Logical, allow parallel bootstrap evaluation when the
|
ci_level |
Confidence level for reported intervals. |
A list with the executed results and metadata describing the enhancements that were applied.
run_benchmark_suite() evaluates a selection of
heteroscedasticity diagnostics across varying sample sizes while measuring
runtime, memory allocation, and statistical agreement with the
lmtest and car packages. The companion
generate_benchmark_report() helper aggregates the raw output into tidy
summary tables and recommendations.
run_benchmark_suite( sample_sizes = c(100L, 500L, 1000L, 10000L, 100000L, 1000000L), tests = NULL, replicates = 3L, hetero_patterns = c("none", "linear", "group"), hetero_strength = 1, baseline_packages = c("lmtest", "car"), seed = 123L, n_predictors = 4L, profile_memory = TRUE, progress = interactive() ) generate_benchmark_report(benchmark_results, accuracy_tolerance = 1e-4)run_benchmark_suite( sample_sizes = c(100L, 500L, 1000L, 10000L, 100000L, 1000000L), tests = NULL, replicates = 3L, hetero_patterns = c("none", "linear", "group"), hetero_strength = 1, baseline_packages = c("lmtest", "car"), seed = 123L, n_predictors = 4L, profile_memory = TRUE, progress = interactive() ) generate_benchmark_report(benchmark_results, accuracy_tolerance = 1e-4)
sample_sizes |
Integer vector of observation counts to benchmark. Values may range from a few hundred observations to one million. |
tests |
Optional character vector restricting the benchmark to specific
diagnostics (currently |
replicates |
Scalar integer applied to all sample sizes or an integer
vector matching |
hetero_patterns |
Character vector describing the heteroscedasticity
patterns used when generating synthetic data. Supported values are
|
hetero_strength |
Positive numeric multiplier controlling the severity of variance heterogeneity. |
baseline_packages |
Character vector of external packages used for comparisons. Missing dependencies are skipped and reported in the metadata. |
seed |
Integer seed passed to the data generator for reproducibility. |
n_predictors |
Number of regressors (excluding the intercept) used when simulating benchmark datasets. |
profile_memory |
Logical; when |
progress |
Logical indicating whether to display a textual progress bar during execution. |
benchmark_results |
List returned by |
accuracy_tolerance |
Non-negative numeric tolerance for declaring statistical agreement with reference implementations (based on absolute p-value differences). |
Datasets are generated from a linear regression model with a configurable number of predictors and variance patterns (none, linear, group, or exponential). Each diagnostic from heteroTests is executed alongside equivalent tests from lmtest and car when available. Memory profiling is enabled via bench when installed; otherwise only runtimes are collected. The output is suitable for regression testing (to detect performance regressions) and for building artefacts such as CSV benchmark reports.
run_benchmark_suite() returns a list with four elements:
Data frame containing runtime, memory, and inference metrics for every test, sample size, and replicate.
Data frame recording absolute differences in p-values and test statistics relative to each baseline implementation.
List of aggregated medians for quick inspection of speed, memory, and accuracy.
Metadata describing the benchmark configuration (sample sizes, baselines, seed, and availability of optional dependencies).
generate_benchmark_report() converts the raw results into aggregated
speed, memory, accuracy, recommendation, and scalability tables alongside the
original metadata.
if (requireNamespace("lmtest", quietly = TRUE) && requireNamespace("car", quietly = TRUE)) { results <- run_benchmark_suite( sample_sizes = c(100L, 250L), replicates = 1L, profile_memory = FALSE, progress = FALSE ) report <- generate_benchmark_report(results) head(report$recommendations) }if (requireNamespace("lmtest", quietly = TRUE) && requireNamespace("car", quietly = TRUE)) { results <- run_benchmark_suite( sample_sizes = c(100L, 250L), replicates = 1L, profile_memory = FALSE, progress = FALSE ) report <- generate_benchmark_report(results) head(report$recommendations) }
Run registered diagnostic plots
runDiagnosticPlots( model, plots = c("residuals_fitted", "spread_level", "density", "qq", "bubble_variance") )runDiagnosticPlots( model, plots = c("residuals_fitted", "spread_level", "density", "qq", "bubble_variance") )
model |
A fitted |
plots |
Character vector of plot names to generate |
Named list of ggplot objects
runDiagnosticPlots(lm(mpg ~ wt, mtcars))runDiagnosticPlots(lm(mpg ~ wt, mtcars))
Combines heteroscedasticity checks with tests for collinearity, nonlinearity and influential observations.
runDiagnostics( model, data = NULL, tests = c("white", "breusch_pagan"), power = 2:3, use_cache = TRUE, chunk_threshold_mb = 100, chunk_size = 10000, progress = interactive() )runDiagnostics( model, data = NULL, tests = c("white", "breusch_pagan"), power = 2:3, use_cache = TRUE, chunk_threshold_mb = 100, chunk_size = 10000, progress = interactive() )
model |
A fitted |
data |
Optional data frame if |
tests |
Heteroscedasticity tests to run. |
power |
Powers for |
use_cache |
Logical flag forwarded to |
chunk_threshold_mb |
Numeric threshold passed to |
chunk_size |
Integer chunk size supplied to |
progress |
Logical flag controlling whether textual progress indicators are displayed during long-running operations. |
A list with the results of all diagnostics.
data(mtcars) runDiagnostics(mpg ~ wt + qsec, mtcars)data(mtcars) runDiagnostics(mpg ~ wt + qsec, mtcars)
Convenience wrapper that executes several heteroscedasticity tests on a fitted linear model.
runHeteroTests( model, data = NULL, tests = c("white", "breusch_pagan"), use_cache = TRUE, chunk_threshold_mb = 100, chunk_size = 10000, progress = interactive() )runHeteroTests( model, data = NULL, tests = c("white", "breusch_pagan"), use_cache = TRUE, chunk_threshold_mb = 100, chunk_size = 10000, progress = interactive() )
model |
an object of class |
data |
optional data frame used to fit |
tests |
character vector of test names to run: any of the names |
use_cache |
logical indicating whether cached results should be reused when available. Requires the digest
package and defaults to |
chunk_threshold_mb |
numeric threshold (in megabytes) above which streaming implementations are preferred for supported diagnostics. |
chunk_size |
integer number of observations processed per chunk when streaming diagnostics. |
progress |
logical flag controlling whether textual progress bars are displayed when running multiple diagnostics. |
By default runs performWhiteTest and performBPTest, but additional tests can be requested. Custom diagnostics registered via registerDiagnostic are also available.
A named list of htest objects.
White, H. (1980). A heteroskedasticity-consistent covariance matrix estimator and a direct test for heteroskedasticity. Econometrica, 48(4), 817–838. Breusch, T. S., & Pagan, A. R. (1979). A Simple Test for Heteroscedasticity and Random Coefficient Variation. Econometrica, 47(5), 1287–1294.
data(mtcars) m <- lm(mpg ~ wt + qsec, data = mtcars) # Default: White and Breusch-Pagan runHeteroTests(m, mtcars) # Specify additional diagnostics runHeteroTests(m, mtcars, tests = c("white", "koenker", "ncv")) custom <- function(model, data) list(stat = 1) registerDiagnostic("custom", custom) runHeteroTests(m, mtcars, tests = c("white", "custom"))data(mtcars) m <- lm(mpg ~ wt + qsec, data = mtcars) # Default: White and Breusch-Pagan runHeteroTests(m, mtcars) # Specify additional diagnostics runHeteroTests(m, mtcars, tests = c("white", "koenker", "ncv")) custom <- function(model, data) list(stat = 1) registerDiagnostic("custom", custom) runHeteroTests(m, mtcars, tests = c("white", "custom"))
Executes a set of registered diagnostics in parallel when multiple CPU cores are available, falling back to sequential execution otherwise.
runHeteroTestsParallel(model, data, tests, n_cores = NULL)runHeteroTestsParallel(model, data, tests, n_cores = NULL)
model |
Fitted model object passed to each diagnostic. Must be compatible
with the internal |
data |
Data frame used to fit |
tests |
Character vector naming the diagnostics to execute. |
n_cores |
Optional positive integer giving the number of worker processes
to spawn. Defaults to |
When n_cores exceeds one and the parallel package is available, the helper
evaluates the diagnostics via parallel::parLapply() after exporting the
model and data to the worker environment. On systems without fork support the
function gracefully reverts to sequential execution.
Named list of test results in the order provided by tests.
cachedTest() for memoised execution of individual diagnostics.
Convenience wrapper for multivariate tests such as Box's M.
runMultivariateTests(data, group, tests = c("box_m"))runMultivariateTests(data, group, tests = c("box_m"))
data |
Numeric data frame or matrix with multiple variables. |
group |
Factor defining groups. |
tests |
Character vector of test names. |
A named list of htest objects.
runMultivariateTests(iris[,1:4], iris$Species)runMultivariateTests(iris[,1:4], iris$Species)
Breusch-Pagan LM and Pesaran CD tests for panel models.
runPanelTests(model, data, id, time = NULL, tests = c("bp_random", "pesaran"))runPanelTests(model, data, id, time = NULL, tests = c("bp_random", "pesaran"))
model |
A fitted |
data |
Data frame used to fit |
id |
Column identifying individuals. |
time |
Column identifying time periods for the Pesaran test. |
tests |
Character vector of test names. |
A named list of htest objects.
df <- data.frame(id = rep(1:3, each = 4), time = rep(1:4, 3), x = runif(12), y = rnorm(12)) m <- lm(y ~ x, data = df) runPanelTests(m, df, id = "id", time = "time")df <- data.frame(id = rep(1:3, each = 4), time = rep(1:4, 3), x = runif(12), y = rnorm(12)) m <- lm(y ~ x, data = df) runPanelTests(m, df, id = "id", time = "time")
A convenience wrapper that takes the data out of a
survey::svydesign() object, fits the model by ordinary least squares and
runs runHeteroTests. It does not use the sampling
weights, strata or clusters of the design, and warns when the design has
unequal weights or clusters.
runSurveyHeteroTests(formula, design, tests = c("white", "breusch_pagan"), ...)runSurveyHeteroTests(formula, design, tests = c("white", "breusch_pagan"), ...)
formula |
Model formula specifying the mean structure. |
design |
A |
tests |
Diagnostic names passed on to |
... |
Additional arguments forwarded to |
The tests are the ones runHeteroTests runs on any lm: they
treat the observations as an independent sample with equal weights. They hold
their level on survey data when the design can be ignored given the regressors,
that is when the chance of being sampled depends only on variables in the
model, and the sample has no clusters. When selection depends on the response,
or observations are clustered, they reject a model with constant error variance
far more often than their nominal level.
The package has no design-based test of constant variance. Sampling weights are
not precision weights: they say how many population units an observation stands
for and nothing about its error variance. Passing them to
lm(weights = ), or testing a survey::svyglm() fit, makes the
tests examine residuals multiplied by the square roots of the weights, and a
homoscedastic model is then rejected whenever the weights vary with the
regressors. svyglm fits are refused for that reason.
inst/validation/survey-designs-size.R measures all of this, together
with two design-based tests that were tried and not adopted because they
reject too often at the sample sizes examined.
An object of class hetero_test_suite.
Up to 0.12.0 this page described a survey-weighted fit. The weights did not reach the fit, which was by ordinary least squares, as it is now, so the reported values are unchanged.
if (requireNamespace("survey", quietly = TRUE)) { data(api, package = "survey") design <- survey::svydesign(id = ~1, strata = ~stype, weights = ~pw, data = apistrat) # Warns: the weights of this design are unequal and are not used. res <- runSurveyHeteroTests(api00 ~ api99 + ell, design) generics::tidy(res) }if (requireNamespace("survey", quietly = TRUE)) { data(api, package = "survey") design <- survey::svydesign(id = ~1, strata = ~stype, weights = ~pw, data = apistrat) # Warns: the weights of this design are unequal and are not used. res <- runSurveyHeteroTests(api00 ~ api99 + ell, design) generics::tidy(res) }
Convenience wrapper for Engle's ARCH LM and McLeod-Li tests.
runTimeSeriesTests(model, lags = 1, tests = c("arch_lm", "mcleod_li"))runTimeSeriesTests(model, lags = 1, tests = c("arch_lm", "mcleod_li"))
model |
A fitted |
lags |
Number of lags for both tests. |
tests |
Character vector of test names. |
A named list of htest objects.
data(mtcars) m <- lm(mpg ~ wt + qsec, mtcars) runTimeSeriesTests(m, lags = 2)data(mtcars) m <- lm(mpg ~ wt + qsec, mtcars) runTimeSeriesTests(m, lags = 2)
Compares the package's test results with established implementations
from other packages (currently lmtest and car). Differences exceeding
the supplied tolerance are flagged.
rvalidate_against_reference(test_name, model, data, tolerance = 1e-06)rvalidate_against_reference(test_name, model, data, tolerance = 1e-06)
test_name |
Character scalar naming the diagnostic: "breusch_pagan", "studentized_bp", or "white". |
model |
A fitted stats::lm object representing the mean specification to be diagnosed. |
data |
A base::data.frame (or object coercible to one) containing the
variables referenced by |
tolerance |
Acceptable absolute difference between statistics and p-values when comparing to the reference implementation. |
A list describing the comparison, including a status field with
values "ok", "mismatch", or "skipped" when the reference package
is unavailable.
Provides a discrete palette used across diagnostic comparisons.
scale_colour_hetero_diagnostic(...) scale_fill_hetero_diagnostic(...)scale_colour_hetero_diagnostic(...) scale_fill_hetero_diagnostic(...)
... |
Arguments passed to |
A ggplot2 scale.
ggplot2::ggplot(mtcars, ggplot2::aes(wt, mpg, colour = factor(cyl))) + ggplot2::geom_point() + scale_colour_hetero_diagnostic()ggplot2::ggplot(mtcars, ggplot2::aes(wt, mpg, colour = factor(cyl))) + ggplot2::geom_point() + scale_colour_hetero_diagnostic()
Utilities to generate data with non-constant variance patterns. simulate_hetero simulates a linear regression model with heteroscedastic errors using a user-supplied variance function. The helper functions prefixed by sigma_ implement common variance patterns and can be passed to sigma_func. simulate_arch1 creates a simple ARCH(1) time series.
simulate_hetero(n, beta0, beta1, sigma_func, seed = NULL) simulate_arch1(n, mu = 0, alpha0 = 0.5, alpha1 = 0.3, seed = NULL) sigma_linear(x) sigma_exponential(x) sigma_group(x) sigma_piecewise(x) sigma_poly(x, a = 0.5, b = 0.1, c = 0.02) sigma_sin(x, A = 1, B = 0.5, omega = 2 * pi/10, phi = 0) sigma_multiplicative(x, mu_func, p = 1) sigma_spatial(coords, gamma0 = 0.5, gamma1 = 0.1) sigma_logistic(x, L = 2, k = 1, x0 = 5) sigma_inverse(x, a = 1, b = 1) sigma_power(x, a = 0.5, p = 0.5) sigma_step(x, thr = 5, low = 0.5, high = 2) sigma_u_shape(x, a = 0.1, b = 0.05, center = 5) sigma_exp_decay(x, a = 2, b = 0.2) sigma_gaussian_peak(x, base = 0.5, height = 1, mu = 5, sd = 1) sigma_piecewise_linear(x, thr = 5, slope1 = 0.1, slope2 = 0.3)simulate_hetero(n, beta0, beta1, sigma_func, seed = NULL) simulate_arch1(n, mu = 0, alpha0 = 0.5, alpha1 = 0.3, seed = NULL) sigma_linear(x) sigma_exponential(x) sigma_group(x) sigma_piecewise(x) sigma_poly(x, a = 0.5, b = 0.1, c = 0.02) sigma_sin(x, A = 1, B = 0.5, omega = 2 * pi/10, phi = 0) sigma_multiplicative(x, mu_func, p = 1) sigma_spatial(coords, gamma0 = 0.5, gamma1 = 0.1) sigma_logistic(x, L = 2, k = 1, x0 = 5) sigma_inverse(x, a = 1, b = 1) sigma_power(x, a = 0.5, p = 0.5) sigma_step(x, thr = 5, low = 0.5, high = 2) sigma_u_shape(x, a = 0.1, b = 0.05, center = 5) sigma_exp_decay(x, a = 2, b = 0.2) sigma_gaussian_peak(x, base = 0.5, height = 1, mu = 5, sd = 1) sigma_piecewise_linear(x, thr = 5, slope1 = 0.1, slope2 = 0.3)
n |
Number of observations for |
beta0 |
Intercept of the regression. |
beta1 |
Slope of the regression. |
sigma_func |
Function returning the standard deviation for each |
seed |
Optional integer seed for reproducibility. |
mu |
Mean of the ARCH(1) process for |
alpha0 |
Constant term in the ARCH variance equation. |
alpha1 |
ARCH coefficient (must be in [0,1)). |
x |
Numeric vector used by the |
coords |
Matrix or data frame with columns |
mu_func |
Function returning mean values for |
p |
Exponent for |
a, b, c, A, B, omega, phi, L, k, x0, thr, low, high, center, base, height, sd, slope1, slope2, gamma0, gamma1
|
Additional numeric parameters controlling the shape of the variance patterns. |
For simulate_hetero a data frame with columns x and y. For simulate_arch1 a data frame with columns time, y and sigma. The sigma_* helpers return numeric vectors of standard deviations.
set.seed(1) hetero <- simulate_hetero(200, 1, 2, sigma_linear) head(hetero) # Other variance patterns simulate_hetero(100, 0, 1, sigma_logistic) simulate_arch1(50)set.seed(1) hetero <- simulate_hetero(200, 1, 2, sigma_linear) head(hetero) # Other variance patterns simulate_hetero(100, 0, 1, sigma_logistic) simulate_arch1(50)
Provides tools for validating heteroscedasticity tests under controlled scenarios and estimating statistical power.
simulate_type_I_errors( test_function, n_sims = 1000, alpha = 0.05, n_obs = 100, seed = 123 ) simulate_power_analysis( test_function, sigma_functions = list(sigma_linear), effect_sizes = c(0.1, 0.2, 0.5, 1), n_sims = 500, n_obs = 100, alpha = 0.05 )simulate_type_I_errors( test_function, n_sims = 1000, alpha = 0.05, n_obs = 100, seed = 123 ) simulate_power_analysis( test_function, sigma_functions = list(sigma_linear), effect_sizes = c(0.1, 0.2, 0.5, 1), n_sims = 500, n_obs = 100, alpha = 0.05 )
test_function |
Function taking a model and data and returning an
object with a numeric |
n_sims |
Number of simulation replications. |
alpha |
Significance level for Type I error or power calculations. |
n_obs |
Number of observations for generated datasets. |
seed |
Optional integer seed for reproducibility. |
sigma_functions |
List of variance functions generating heteroscedastic patterns. |
effect_sizes |
Numeric vector of effect size multipliers. |
A list summarising Type I error rate or a data frame of power estimates.
Generate standardized error message
std_error(type, ...)std_error(type, ...)
type |
Error message type. |
... |
Named arguments to replace in the template. |
Stops execution with a formatted message.
Generate standardized warning message
std_warning(type, ...)std_warning(type, ...)
type |
Warning message type. |
... |
Named arguments for the template. |
Issues a warning with a formatted message.
Given diagnostic test results from runHeteroTests(), this helper
provides a basic summary of recommended follow-up steps. It evaluates the
number of significant tests and proposes variance stabilising
transformations or modelling approaches.
suggestRemediation(diagnostic_results) ## S3 method for class 'remediation_suggestions' print(x, ...)suggestRemediation(diagnostic_results) ## S3 method for class 'remediation_suggestions' print(x, ...)
diagnostic_results |
Named list of |
x |
Object of class |
... |
Not used. |
The function counts how many diagnostic tests yield a p-value below 0.05. If none are significant it returns a brief conclusion that no action is needed. Otherwise a severity level is assigned and appropriate transformations or variance modelling approaches are suggested.
An object of class remediation_suggestions containing a summary
of potential actions.
data(mtcars) mod <- lm(mpg ~ wt + qsec, data = mtcars) res <- runHeteroTests(mod, mtcars) suggestRemediation(res)data(mtcars) mod <- lm(mpg ~ wt + qsec, data = mtcars) res <- runHeteroTests(mod, mtcars) suggestRemediation(res)
Summarize diagnostic test results.
## S3 method for class 'HeteroDiagnostic' summary(object, tests = c("white", "breusch_pagan"), ...)## S3 method for class 'HeteroDiagnostic' summary(object, tests = c("white", "breusch_pagan"), ...)
object |
A |
tests |
Character vector naming the diagnostics to summarise. |
... |
Further arguments passed to the individual tests. |
Named numeric vector of test statistics.
Users can register new tests via this object. Built-in tests are pre-registered at package load time.
Run the registered diagnostics on the model.
test(object, ...)test(object, ...)
object |
A |
... |
Further arguments passed to the individual tests. |
List of test results.
Provides a registry of heteroscedasticity tests with metadata and
convenience methods to run them with input validation. This is an
alternative to the older environment-based registry used by
runHeteroTests().
The shared instance test_factory can be used to register new tests
and execute them. See register and run_test methods
for details.
register()
TestFactory$register(name, func, metadata = list())
nameName of the test
funcFunction with arguments model and data
metadataOptional list with metadata fields
Invisibly returns the factory Get available tests
get_available()
TestFactory$get_available(data_type = NULL, min_n = NULL)
data_typeFilter by supported data type
min_nFilter by minimum observations
Character vector of test names Run a registered test
run_test()
TestFactory$run_test(test_name, model, data, ...)
test_nameName of the test
modelFitted model
dataData frame used to fit the model
...Additional arguments passed to the test
Result of the test
clone()
The objects of this class are cloneable with this method.
TestFactory$clone(deep = FALSE)
deepWhether to make a deep clone.
Applies a light-minimal theme with subtle gridlines and bold titles to maintain visual consistency across diagnostic plots.
theme_hetero(base_size = 12, base_family = "")theme_hetero(base_size = 12, base_family = "")
base_size |
Base font size. |
base_family |
Base font family. |
A ggplot2::theme object.
theme_hetero()theme_hetero()
Tidy, glance and augment methods integrating heteroscedasticity diagnostics with the broom generics from the generics package.
## S3 method for class 'hetero_test' tidy(x, ...) ## S3 method for class 'hetero_test' glance(x, ...) ## S3 method for class 'hetero_test' augment(x, data = NULL, ...) ## S3 method for class 'hetero_test_suite' tidy(x, ...) ## S3 method for class 'hetero_test_suite' glance(x, ...) ## S3 method for class 'hetero_test_suite' augment(x, data = NULL, ...) ## S3 method for class 'hetero_grouped_suite' tidy(x, ...)## S3 method for class 'hetero_test' tidy(x, ...) ## S3 method for class 'hetero_test' glance(x, ...) ## S3 method for class 'hetero_test' augment(x, data = NULL, ...) ## S3 method for class 'hetero_test_suite' tidy(x, ...) ## S3 method for class 'hetero_test_suite' glance(x, ...) ## S3 method for class 'hetero_test_suite' augment(x, data = NULL, ...) ## S3 method for class 'hetero_grouped_suite' tidy(x, ...)
x |
Heteroscedasticity diagnostic result(s) returned by
|
data |
Optional data frame used to augment diagnostics; defaults to the data embedded within the fitted model when available. |
... |
Passed through for compatibility. |
A data frame summarising the diagnostic(s), or an augmented data set containing fitted values and residuals alongside the original predictors.
tidy returns one row per test. parameter is the first parameter
of the test and parameter2 the second, for a test that has two (the
denominator degrees of freedom of an F statistic, or the number of bootstrap
replications); it is NA otherwise. estimate is given when the
test reports exactly one estimate. Up to 0.12.0 a test with two parameters was
returned as two rows.
generics::tidy, generics::glance, generics::augment
if (requireNamespace("generics", quietly = TRUE)) { data(mtcars) fit <- lm(mpg ~ wt + qsec, data = mtcars) suite <- runHeteroTests(fit, mtcars, tests = c("white", "breusch_pagan")) generics::tidy(suite) }if (requireNamespace("generics", quietly = TRUE)) { data(mtcars) fit <- lm(mpg ~ wt + qsec, data = mtcars) suite <- runHeteroTests(fit, mtcars, tests = c("white", "breusch_pagan")) generics::tidy(suite) }
Provides the compatibility wrapper used by the public testing interface to ensure that fitted-model objects and their associated data satisfy minimal quality requirements. The helper guards against the most common issues that invalidate heteroscedasticity tests and produces actionable error messages that reference the calling diagnostic.
validateTestInputs(model, data, test_name, min_obs = 10)validateTestInputs(model, data, test_name, min_obs = 10)
model |
A fitted model created by |
data |
A |
test_name |
Character scalar naming the diagnostic that is about to run; included in error messages for clarity. |
min_obs |
Non-negative integer giving the minimum sample size accepted
by the diagnostic. Defaults to |
The routine performs four layers of validation:
confirm that model inherits from lm or glm and that its
coefficients and residuals are finite;
verify that data is a data.frame with at least min_obs rows;
ensure the residual vector is available, finite, and aligned with the supplied data;
emit warnings when studentised residuals exceed five standard deviations in absolute value or when the dataset is very large (more than 10,000 observations).
Results are cached (when the digest package is installed) so repeated calls with unchanged inputs return immediately.
Invisibly returns TRUE when validation succeeds. Execution stops
with an informative error when any check fails.
Fox, J. (2015). Applied Regression Analysis and Generalized Linear Models (3rd ed.). SAGE.
Belsley, D. A., Kuh, E., & Welsch, R. E. (1980). Regression Diagnostics: Identifying Influential Data and Sources of Collinearity. Wiley.
checkModel(), checkModelEnhanced(), rvalidateModelInputs(),
rvalidateTestRequirements()
data(mtcars) lm_fit <- stats::lm(mpg ~ wt + hp, data = mtcars) validateTestInputs(lm_fit, mtcars, "white") noisy <- mtcars noisy$mpg[1] <- 100 outlier_fit <- stats::lm(mpg ~ wt + hp, data = noisy) validateTestInputs(outlier_fit, noisy, "white")data(mtcars) lm_fit <- stats::lm(mpg ~ wt + hp, data = mtcars) validateTestInputs(lm_fit, mtcars, "white") noisy <- mtcars noisy$mpg[1] <- 100 outlier_fit <- stats::lm(mpg ~ wt + hp, data = noisy) validateTestInputs(outlier_fit, noisy, "white")