Implementation of the Hausdorff-Adaptive Filter (HAF) algorithm from the paper:
"Robust Online Learning in Non-Stationary Markets: A Credal Set Approach with Uncertainty Quantification"
This implementation is publication-ready and reproduces key paper results:
# Reproduce Tables 1-3 with statistical validation
python reproduce_paper.pyβ Includes:
- All baseline methods (BOCPD, HMM, RMV, BOL)
- Bootstrap confidence intervals
- Statistical significance tests (p-values)
- Negative results (high-SNR environments)
See REPRODUCTION.md for detailed reproduction guide.
HAF is an online learning algorithm designed for regime detection and adaptive decision-making in non-stationary environments (especially financial markets). It uses credal sets (convex sets of probability distributions) to quantify epistemic uncertainty and detect regime changes through contraction ratio monitoring.
- Epistemic Uncertainty Quantification: Uses credal sets to distinguish between uncertainty due to lack of data vs. inherent randomness
- Automatic Regime Detection: Monitors Hausdorff contraction ratios to detect regime shifts without manual tuning
- Principled Risk Management: Automatically scales positions based on credal set diameter (epistemic uncertainty)
- Theoretical Guarantees: Geometric convergence in stable regimes, probabilistic regime detection bounds
In stable market regimes, credal sets contract geometrically toward a fixed point. When a regime shift occurs, this contractivity breaks down - the credal set expands rather than contracts, providing an early warning signal.
# Clone the repository
git clone https://github.com/yourusername/haf-implementation.git
cd haf-implementation
# Install dependencies
pip install -r requirements.txt
# Optional: For real data experiments
pip install yfinancefrom haf_core import HausdorffAdaptiveFilter
import numpy as np
# Initialize HAF
haf = HausdorffAdaptiveFilter(
n_assets=1,
rho_thresh=0.95, # Stable regime threshold
rho_reset=1.2, # Regime shift threshold
window=10 # Moving average window
)
# Online learning loop
for observation in market_data:
# Update with new observation
regime, position_scale = haf.update(observation)
# Get recommended action (portfolio weights)
action = haf.get_action()
# Scale position based on uncertainty
final_position = action * position_scale
# Get monitoring metrics
metrics = haf.get_metrics()
print(f"Regime: {regime}, Uncertainty: {metrics['diameter']:.4f}")# Run complete reproduction suite
python reproduce_paper.py
# Run basic demo
python demo.py
# Run tests
pytest tests/ -vhaf-implementation/
βββ README.md # This file
βββ REPRODUCTION.md # Paper reproduction guide (NEW)
βββ requirements.txt # Dependencies
βββ haf_core.py # Core HAF implementation
βββ baselines.py # Baseline methods (BOCPD, HMM, RMV, BOL) (NEW)
βββ statistical_utils.py # Bootstrap CI, p-values (NEW)
βββ data_loader.py # Data loading utilities (NEW)
βββ reproduce_paper.py # Paper reproduction script (NEW)
βββ demo.py # Basic demo
βββ tests/
β βββ test_haf.py # Unit tests
βββ examples/
β βββ multi_asset_example.py # Multi-asset portfolio example
βββ docs/
βββ QUICK_START.md # Quick start guide
βββ USAGE_EXAMPLES.md # Usage examples
βββ PROJECT_STRUCTURE.md # Code organization
βββ TEST_DOCUMENTATION.md # Test documentation
Represents a convex set of probability distributions through K extreme distributions (typically K=3):
- Bull regime: Positive mean, low volatility
- Bear regime: Negative mean, high volatility
- Neutral regime: Zero mean, medium volatility
credal_set = CredalSet([bull_dist, bear_dist, neutral_dist])
diameter = credal_set.diameter() # Epistemic uncertainty measureThe Hausdorff metric measures the "distance" between two credal sets:
d_H = credal_set_t.hausdorff_distance(credal_set_{t-1})The key signal for regime detection:
Ο_t = d_H(P_t, P_{t-1}) / d_H(P_{t-1}, P_{t-2})
- Ο < 1: Contracting (stable regime)
- Ο β 1: Uncertain
- Ο > 1.2: Expanding (regime shift detected!)
Choose actions that maximize worst-case expected utility across all distributions in the credal set:
action = argmax_a min_{P β credal_set} E_P[utility(a)]| Parameter | Default | Description |
|---|---|---|
rho_thresh |
0.95 | Threshold for identifying stable regimes |
rho_reset |
1.2 | Threshold for detecting regime shifts |
window |
10 | Moving average window for Ο smoothing |
safety_factor |
0.3 | Position scaling during detected regime shifts |
In stable regimes, credal sets converge geometrically:
E[d_H(P_t, P*)] β€ d_H(P_0, P*) Β· Ο^t
where Ο < 1 is the contraction rate.
When a regime shift occurs with separation Ξ:
P(Ο_t β₯ 1 + Ξ΄) β₯ 1 - exp(-cΒ·nΒ·ΞΒ²/ΟΒ²)
Larger regime changes are detected with higher probability.
Cumulative regret is controlled by epistemic uncertainty:
R_T β€ U_max Β· d_H(P_0, {P*}) Β· (1-Ο^T)/(1-Ο)
Recommended for:
- Non-stationary environments with regime shifts
- Need for interpretable uncertainty quantification
- Moderate transaction costs (< 10 basis points)
- Daily or lower frequency rebalancing
May not help when:
- Extended stable regimes with high signal-to-noise
- Very high transaction costs (> 20 bps)
- High-frequency trading requirements
The paper suggests several extensions:
- Decompose epistemic vs. aleatoric uncertainty formally
- Incorporate transaction costs into theoretical guarantees
- Scale to high dimensions via factor models
- Applications beyond finance: robotics, healthcare, recommendation systems
If you use this implementation, please cite:
MIT License - see LICENSE file for details
Contributions are welcome! Please feel free to submit a Pull Request.
For questions or issues, please open an GitHub issue or contact the maintainer.
Note: This is a research implementation for educational purposes. Not intended for production trading without proper risk management and validation.