nctest
Noise-corrected tests of predictive ability for high-dimensional forecasting models.
When a benchmark forecast is enlarged with many predictors and fitted by ridge, the
Clark–West test asks whether the extra predictors carry any signal. A forecaster usually wants
to know something else: whether the enlarged model forecasts better once its estimation noise
is paid for. The two questions have different answers when the model is large relative to
the estimation window. nctest implements the noise-corrected (CC) test of Fallahgoul (2026),
which targets the second question, and reports it next to Diebold–Mariano and Clark–West.
Install
pip install nctest
The only dependency is NumPy.
Example: a HAR benchmark enlarged with extra lags
import numpy as np
import nctest
x = np.log(rv) # daily realized variance, your data
y, H, X = nctest.har_design(x, extra_lags=24) # HAR regressors and lags 2..25
res = nctest.compare(y, X, benchmark=H, window=250, penalty=0.01)
print(res)
On a simulated series where the HAR is the true model (examples/har_example.py):
Noise-corrected test of predictive ability
forecasts n = 3725, Bartlett bandwidth = 9
window T = 250, features P = 24, penalty z = 0.01 (ztil = zT/P = 0.104167)
MSPE benchmark 0.179374, candidate 0.197627, gap -0.1018
mean Psihat 0.1042, sanity ratio R 0.96
statistic t
Diebold-Mariano -9.80
Clark-West -0.49
CC, window variance -0.05
CC, difference variance -3.06
* exceeds the one-sided 5% critical value 1.645
decision (reject only if both CC tests reject): do not reject H0
The summary also prints notes on the sanity ratio and the bandwidth condition when they apply.
res.reject is the decision of the intersection rule (both CC statistics reject at 5%).
The other fields of res hold every statistic, the sanity ratio and the out-of-sample
mean-square gap.
What compare does
Row t of X and of the benchmark matrix H holds the predictors used to forecast y[t],
so lag them before the call. At each origin the benchmark is fitted by least squares on the
last window observations. The candidate adds a ridge fit of the benchmark's residuals on
the extra predictors, residualised on the benchmark regressors, with penalty z in
$$\frac1T\sum_s (\hat u_s - \tilde x_s'\gamma)^2 + z|\gamma|^2 .$$
The two models are nested, and the candidate's increment is linear in the training targets, $\hat y_{2,t}-\hat y_{1,t}=a_t'Y_{t-1}$. The test statistic is built from
$$d^{CC}t = e{1,t}^2 - e_{2,t}^2 + \hat\sigma^2_t,\hat\Psi_t, \qquad \hat\Psi_t = |a_t|^2,$$
studentised by a Bartlett long-run variance. benchmark may also be "mean" (rolling mean)
or "zero".
Your own forecasts
If your models are linear smoothers of the training targets but not ridge, compute the weights $a_t$ yourself and call
res = nctest.from_forecasts(y, yhat1, yhat2, psi=nctest.psihat(A), sigma2_w=s2w)
The building blocks (cc_test, dm_cw, sigma2_window, sigma2_difference,
sanity_ratio, intersection, bartlett_lrv) are exported for custom designs.
Reading the output
- Sanity ratio R. In population R cannot fall below one. A value below one means the correction exceeds the whole forecast increment, and the test is mis-scaled for that design.
- Bandwidth condition. The paper's sufficient condition is $T=o(n^{1/3})$. Most applications violate it; Section 5.6 of the paper measures size in that regime.
- Own-lag designs. When the extra predictors are lags of the target, as in the HAR example, the correction is accurate only to the extent the paper's scope condition holds; Section 4 of the paper measures it for designs of this kind.
Reference
Fallahgoul, H. (2026). Noise-Corrected Tests for High-Dimensional Forecasting Models. Replication package: https://github.com/hfallahgoul/noise-corrected-tests
Licence
MIT.
Metadata
Release files for nctest 0.1.0
For a detailed explanation of source distributions (sdists) and built distributions (wheels), please see the package formats documentation.
Source distribution (sdist)
| File | Size | Uploaded | Provenance | |
|---|---|---|---|---|
| nctest-0.1.0.tar.gz | 13.5 kB | Without provenance | Details |
Built distribution (wheel)
| File | Interpreter | ABI | Platform | Reset |
|---|---|---|---|---|
| nctest-0.1.0-py3-none-any.whl | Python 3 | none | any | Details |
Total release size: 25.3 kB
Release files / nctest-0.1.0.tar.gz
| Download URL | nctest-0.1.0.tar.gz |
|---|---|
| Size | 13.5 kB |
| Tags | Source |
|
SHA-256 checksum How to use checksums |
18446ebf09aeeea5f5e445753595f6e70bbec2f4931e800df5b028eb84ee9b19
|
|
BLAKE2b-256 checksum How to use checksums |
7575a70d6b672d55e06a2e4e32c49a0b83547277dca88e839de48ce590c07e54
|
| Upload date | |
|
Uploaded using Trusted Publishing? What is trusted publishing? |
No |
| Uploaded via |
twine/6.2.0 CPython/3.9.7
|
Release files / nctest-0.1.0-py3-none-any.whl
| Download URL | nctest-0.1.0-py3-none-any.whl |
|---|---|
| Size | 11.8 kB |
| Tags | Python 3 |
|
SHA-256 checksum How to use checksums |
beec435da5c9af21442ab0b98df90c4a0c55fe7bce48103f8224d5d647354e26
|
|
BLAKE2b-256 checksum How to use checksums |
b3be3ea12fd21d9ac5c8c2329b4a2f382494ad1fbda51306d75dd68385977642
|
| Upload date | |
|
Uploaded using Trusted Publishing? What is trusted publishing? |
No |
| Uploaded via |
twine/6.2.0 CPython/3.9.7
|
Security for nctest 0.1.0
Provenance
Provenance describes where a file came from. On PyPI, provenance is shared via attestations, which provide a verifiable record of the build or publishing details. View details, limitations and caveats.
No provenance found
None of the files in this release were uploaded with provenance metadata.
A note on package security
PyPI is a repository for distributing packages, not a service for auditing them. While third-party security researchers and our staff do their best to detect and remove malicious packages, PyPI cannot guarantee the quality, security or suitability of any given package.
To learn more about protecting yourself from malicious actors, visit our package security documentation.