Metadata-Version: 2.4
Name: pyAssetCorr
Version: 0.1.1
Summary: Estimate asset correlation from historical default data under the Vasicek credit-portfolio model.
Project-URL: Homepage, https://github.com/ZigzagLi/pyAssetCorr
Project-URL: Documentation, https://github.com/ZigzagLi/pyAssetCorr/blob/main/docs/USER_GUIDE.md
Project-URL: Source, https://github.com/ZigzagLi/pyAssetCorr
Author-email: Likai Li <li.likai.1990@gmail.com>
License: MIT
License-File: LICENSE
Keywords: Vasicek,asset correlation,credit risk,default correlation,maximum likelihood,method of moments
Classifier: Development Status :: 4 - Beta
Classifier: Intended Audience :: Financial and Insurance Industry
Classifier: Intended Audience :: Science/Research
Classifier: License :: OSI Approved :: MIT License
Classifier: Programming Language :: Python :: 3
Classifier: Topic :: Scientific/Engineering :: Mathematics
Requires-Python: >=3.9
Requires-Dist: numpy>=1.22
Requires-Dist: scipy>=1.8
Provides-Extra: accel
Requires-Dist: numba>=0.57; extra == 'accel'
Provides-Extra: dev
Requires-Dist: pytest>=7.0; extra == 'dev'
Description-Content-Type: text/markdown

# pyAssetCorr

Estimate **asset correlation** from historical default data under the Vasicek
credit-portfolio model.

A clean-room Python implementation of the most-used functionality of the R
package [`AssetCorr`](https://cran.r-project.org/package=AssetCorr): method-of-moments
and maximum-likelihood estimators for intra- and inter-cohort asset correlation,
with standard errors, information criteria, likelihood-ratio tests, and tools
for overlapping multi-year cohorts.

See [`docs/USER_GUIDE.md`](docs/USER_GUIDE.md) for the full guide.

## Why asset correlation?

In the Vasicek single-factor model an obligor's latent asset return is

```
A = sqrt(rho) * X + sqrt(1 - rho) * eps
```

with a systematic factor `X` shared across obligors and idiosyncratic `eps`.
The obligor defaults when `A` falls below `Phi^{-1}(PD)`. The **asset
correlation** `rho` controls how strongly defaults cluster: it drives the tail
of the portfolio loss distribution and hence economic and regulatory capital.
`pyAssetCorr` estimates `rho` (and, for several cohorts, the inter-cohort
coupling) from observed default-count time series.

## Installation

```bash
pip install pyAssetCorr            # core: numpy + scipy
pip install "pyAssetCorr[accel]"   # optional numba acceleration
```

From a checkout:

```bash
pip install -e ".[dev]"            # editable install with pytest
```

Requires Python >= 3.9. The optional `numba` JIT speeds up the hot
log-likelihood kernel; a pure-NumPy fallback runs transparently when numba is
absent or incompatible with your interpreter.

## Quickstart

Data are two equal-length arrays: `d` = defaults per period, `n` = obligors per
period.

```python
import numpy as np
from pyassetcorr import intra_fmm, intra_mle, simulate_default_series

# Simulate a 10-year history with rho = 0.15, PD = 3%, 2000 obligors/year.
d, n = simulate_default_series(rho=0.15, pd=0.03, n=2000, T=10, seed=0)

# Method of moments (finite-sample corrected) with a confidence interval.
mom = intra_fmm(d, n, ci=True)
print(mom)                 # MomentResult(method='fmm', rho=..., se=..., ...)
print(mom.rho, mom.ci)

# Maximum likelihood, jointly estimating PD, with AIC/BIC and SE.
mle = intra_mle(d, n, pd="joint", ci=True)
print(mle.params["rho"], mle.params["pd"])
print(mle.aic, mle.bic, mle.se["rho"])

# The MLE integral is adaptive; pass `nodes` to check quadrature convergence,
# e.g. intra_mle(d, n, nodes=64). See the User Guide, "Checking quadrature
# convergence".
```

### Several cohorts at once

```python
from pyassetcorr import multi_cohort_mle, lr_test, multi_cohort_single_factor

# d, n are now (T x K): T periods, K cohorts.
fit = multi_cohort_mle(d_mat, n_mat)          # per-cohort rho + free gamma
print(fit.params["rho"], fit.params["gamma"])
print(fit.inter_corr)                          # inter-cohort asset-corr matrix

# Is a single common factor (gamma = 1) enough?
restricted = multi_cohort_single_factor(d_mat, n_mat)
print(lr_test(fit, restricted))                # likelihood-ratio test
```

The multi-cohort model nests cohorts under a single global factor `Z` plus
per-cohort factors `w_k`, controlled by one coupling parameter `gamma`:
intra-cohort correlation stays `rho_k`, inter-cohort correlation is
`gamma * sqrt(rho_i * rho_j)`. `gamma = 1` is a single common factor,
`gamma = 0` independent cohorts.

### Overlapping multi-year cohorts

Annual cohorts measured over an `h`-year horizon share calendar shocks, so the
default series is autocorrelated and naive standard errors are too small. Use a
HAC lag or non-overlapping subsample averaging:

```python
from pyassetcorr import intra_fmm, group_average

intra_fmm(d, n, lag=h - 1)        # autocorrelation-robust (Frei-Wunsch) SE
group_average(d, n, horizon=h)    # average over non-overlapping subsamples
```

## Estimators

| Function | Kind | Description |
|---|---|---|
| `intra_amm` | MoM | Asymptotic method of moments (Gordy 2000) |
| `intra_fmm` | MoM | Finite-sample corrected method of moments |
| `intra_jdp1` | MoM | Unbiased joint-default-probability matching (Lucas 1995) |
| `intra_jdp2` | MoM | Biased JDP matching (literature parity) |
| `intra_mle` | MLE | Single-cohort Vasicek-Binomial MLE |
| `multi_cohort_mle` | MLE | Generalized multi-cohort MLE (nested two-level factor) |

AssetCorr-style aliases (`intraAMM`, `intraFMM`, `intraJDP1`, `intraJDP2`,
`intraMLE`) are provided for discoverability.

## License

MIT. This is a clean-room implementation written from the published equations
(see references below), not a translation of the GPL-3 R source, so it is free
to use in both academic and commercial/financial settings.

## References

- Vasicek, O. (2002). *The Distribution of Loan Portfolio Value.* Risk.
- Gordy, M. (2000). *A comparative anatomy of credit risk models.* J. Banking & Finance.
- Lucas, D. (1995). *Default correlation and credit analysis.* J. Fixed Income.
- Gordy, M. & Heitfield, E. (2010). *Small-sample estimation of models of portfolio credit risk.*
- Duellmann, K. & Gehde-Trapp, M. (2004). *Probability of default estimation.*
- Bluhm, C. & Overbeck, L. (2003). *Systematic risk in homogeneous credit portfolios.*
- Frei, C. & Wunsch, M. (2018). *Moment Estimators for Autocorrelated Time Series and Default Correlations.* J. Credit Risk.
