Momentum vs. Volatility-Targeted S&P 500 Strategies
Top-N momentum vs. S&P 500
Growth of $1 (log), drawdown, and stocks held for an equal-weight momentum portfolio holding the top names by momentum, capped at the size set by the slider — so it holds at most the cap, fewer in months when fewer qualify. Gray = S&P 500 buy-and-hold; equity lines renormalized to $1 at the left edge. Drag horizontally to zoom (leftmost visible point becomes the new $1); double-click to reset. Zooming recomputes the sweep below over the visible window.
Concentration sweep
Results
5-year test
| Strategy | Total | CAGR | Vol | Sharpe | Sortino | Max DD |
|---|---|---|---|---|---|---|
| S&P 500 | 74.56% | 11.83% | 16.93% | 0.75 | 1.02 | -25.43% |
| S&P 500 downside vol | 68.20% | 11.00% | 12.96% | 0.87 | 1.24 | -16.93% |
| S&P 500 EWMA vol | 59.10% | 9.77% | 11.87% | 0.84 | 1.19 | -15.86% |
| S&P 500 vol control | 64.06% | 10.44% | 13.93% | 0.78 | 1.08 | -20.47% |
| Plain momentum | 16.48% | 3.11% | 28.74% | 0.25 | 0.36 | -37.90% |
| Ridge rank | -74.08% | -24.03% | 40.97% | -0.47 | -0.75 | -81.79% |
| Logistic top-decile | -83.36% | -30.58% | 40.31% | -0.70 | -1.13 | -87.67% |
10-year test
| Strategy | Total | CAGR | Vol | Sharpe | Sortino | Max DD |
|---|---|---|---|---|---|---|
| Plain momentum | 299.11% | 14.88% | 28.80% | 0.63 | 0.82 | -44.41% |
| S&P 500 | 251.75% | 13.43% | 18.07% | 0.79 | 0.95 | -33.92% |
| S&P 500 downside vol | 192.26% | 11.34% | 12.14% | 0.95 | 1.21 | -16.93% |
| S&P 500 EWMA vol | 201.63% | 11.70% | 12.80% | 0.93 | 1.19 | -19.27% |
| S&P 500 vol control | 151.89% | 9.70% | 12.10% | 0.83 | 1.03 | -19.37% |
| Ridge rank | 200.49% | 11.75% | 27.00% | 0.55 | 0.74 | -54.94% |
| Logistic top-decile | -15.72% | -1.71% | 36.90% | 0.14 | 0.20 | -86.59% |
Setup & method
- Rebalance at each month-end (stock-selection strategies) or daily (S&P 500 vol-control strategies).
- Adjusted closes for returns; raw volume for liquidity filters.
- Eligibility: price ≥ $5 and 20-day average dollar volume ≥ $1M.
- Excludes commissions, slippage, taxes, cash yield, and market impact.
- S&P 500 strategies use the daily S&P 500 price index (no dividends); buy-and-hold normalized to $1 at each window start.
- Trained models (ridge/logistic) use only data before the selected 5Y or 10Y test window; plain momentum is the untrained baseline.
- All parameter tuning uses a pre-test validation fold (last 20% of pre-test data); benchmark windows are never used for selection.
Concentration sweep
- Plain momentum re-run over the full 1962–2026 history holding the top N names by 12–1 momentum, equal-weight, for N from 1 to all eligible names with positive momentum (“all”, avg ~617/month). Same filters and rebalance as the baseline.
- x and the slider count are the average names actually held per month, not the top-N rank cap — the cap exceeds the eligible positive-momentum universe in most months, so realized holdings run below N (log scale; left = concentrated, right = diversified). Dashed line = the live top-10% rule (~97 names/month avg).
- Metrics computed in-browser from each N's daily returns over the main chart's visible window (full history by default; drag-zoom or the window buttons change it). Grid of 16 log-spaced N; curves are monotone-cubic interpolation between grid points. Vol and total return use log y. The single-name point is omitted from total return (it ends at −100%).
Definitions
Plain momentum
mom = price[t−21] / price[t−252] − 1. Each month, hold the equal-weight top decile by mom among eligible names with mom > 0. No training.
S&P 500 vol control
r = daily S&P 500 return. σ = std(r, 63d) · √252. Exposure w = clip(v* / σ, 0, 1), lagged 1 day. v* ∈ {0.08, 0.10, 0.12, 0.15, 0.18}, chosen to maximize validation-fold Sharpe.
S&P 500 EWMA vol
σ = ewmstd(r, span) · √252. Tune (v*, span), span ∈ {20, 42, 63, 126}.
S&P 500 downside vol
σ = √2 · ewmstd(min(r, 0), span) · √252. w = clip(v* / σ, 0, 1), lagged. Tune (v*, span).
Ridge rank
StandardScaler → Ridge(α=10), fit on the pre-window panel, target = next-month return. Each rebalance, hold the equal-weight top decile by predicted score with mom12−1 > 0.
Features: momentum (12−1, 6−1, 3−1, 1m log-diff), vol63, liquidity (log ADV20, log volume, Δlog-volume, Amihud illiquidity), intraday (log range, close position, gap, upper/lower wick), trend (distance to 252d high, MA50 − MA200).
Logistic top-decile
StandardScaler → LogisticRegression(C=0.25, class_weight=balanced), target = next-month return in the top decile (≥ 90th pct). Same features. Hold the equal-weight top decile by predicted probability with mom12−1 > 0.