Spear GEX Valley モメンタム — 設計根拠と BT 最適化 (2026-03-02)¶
概要¶
SunacchanSpear は "GEX 谷 × モメンタム" の 2 条件が同時成立した瞬間のみ発火する強気 Bull Put Spread 戦略。 25ヶ月 BT でエントリー 0 件という問題を診断・解決した過程で、以下の 2 つの重要な発見があった。
| 発見 | 内容 | 影響 |
|---|---|---|
| モメンタム閾値 | デフォルト 0.5 は厳しすぎ → 0.40 が最適 | エントリー件数 57→71件、BT +\(1,863K→+\)3,653K |
| GEX Valley | ratio_threshold=0.25 は正確に調整済み → 緩和禁止 | GV015 緩和すると最悪 DD -4.6% → -66.1% に悪化 |
GEX Valley(GEX 谷)とは¶
Gamma Exposure の基礎¶
GEX (Gamma Exposure) はマーケットメーカーのガンマポジションの集積度合い。
GEX が高い = ディーラーがガンマを大量保有
→ 株価が上昇するとコールを売り・プットを買う(ヘッジ売り)
→ 株価が下落するとコールを買い・プットを売る(ヘッジ買い)
→ 結果: 株価の変動が抑制される( "pin" される)
GEX が低い(GEX 谷)= ディーラーのガンマ保有が少ない
→ ヘッジ売買が減少
→ 価格が自然なモメンタムで動きやすくなる
GEX 谷 = モメンタムトレードの最適地帯¶
Spear(強気モメンタム戦略)は「GEX が低い(谷)の状態で、かつ強いモメンタムがある」銘柄を狙う。 GEX が高い状態でエントリーするとディーラーのヘッジ売りに圧されてモメンタムが頭打ちになる。
# core/gex.py より
def is_gex_valley(gex_data, ratio_threshold=0.25, nearby_pct=0.20) -> bool:
"""
GEX 谷判定: 市場のガンマ環境がモメンタムトレードに適しているか
ratio_threshold=0.25: |gex_ratio| >= 0.25 のとき True
nearby_pct=0.20: 近傍 GEX が全体の 20% 未満のとき True
両条件が揃うと "GEX 谷" = ディーラーヘッジ圧が低い状態
"""
ratio_threshold = 0.25 の根拠¶
25ヶ月 BT 診断では、Spear エントリー候補 12,999 件のうち 32.7% が gex_valley=False でブロックされていた。
この 0.25 閾値の感度テストで明らかになったこと:
| 閾値 | 結果 | 判定 |
|---|---|---|
| 0.25(デフォルト) | +$3,653K (XS_MT040 単独) | ✅ 最良 |
| 0.15(緩和) | +$3,355K (MT040 + GV015 組み合わせ) | ❌ 悪化 |
| 0.15 単独緩和 | +$1,912K | ❌ ベース同等 |
結論: GEX Valley ratio_threshold=0.25 は過去 4 年のデータで正確にキャリブレーション済み。緩和は禁止。
モメンタム閾値の問題と最適化¶
根本原因の診断¶
Spear エントリー 0 件の主因は モメンタムスコアが常に ≈ 0.0 だったこと。
# 従来の calculate_momentum_score() — close のみ使用
score = (ROC_5 * 0.40) + (RSI_14 * 0.30) + (volume_ratio * 0.30)
# 問題: abs(score) >= 0.5 に達するには以下を「同時」に必要
# ROC_5 ≥ 3.0%/5日 (かなり強い上昇)
# RSI_14 ≥ 70 (買われすぎ水準)
# volume_ratio ≥ 2.0x (出来高 2 倍)
# → これらが同時に成立するケースが 25 ヶ月で 67.3% は score≈0.00
25 ヶ月診断ログのサマリー¶
エントリー候補 12,999 件の内訳:
- score≈0.00 (is_strong_momentum=False) : 67.3% ← 主因
- gex_valley=False : 32.7% ← 副因
合計: エントリー件数 0 件(2024-01〜2026-01)
閾値感度テスト結果(25ヶ月 BT、$13K)¶
| シナリオ | 閾値 | 総資産 | エントリー | 最悪月 DD |
|---|---|---|---|---|
| XS_Base | 0.50 | $1,863K | 57件 | — |
| XS_MT040 | 0.40 | $3,653K | 71件 | -4.6% |
| XS_MT035 | 0.35 | $3,480K | 70件 | — |
| XS_MT025 | 0.25 | $2,047K | 67件 | — |
| XS_MT040_GV015 | 0.40 + GV015 | $3,355K | 69件 | -66.1% |
最適値: threshold = 0.40
OHLCV ベース Spear スコアの実験(Gap / BullControl)¶
実装した代替指標¶
ROC/RSI(close のみ)では検出できない「ギャップアップ + 終値高値寄り」シグナルを補完する目的で
calculate_spear_momentum_ohlcv() を実装・テストした。
def calculate_spear_momentum_ohlcv(bars: List[ChartBar]) -> float:
"""
OHLCV ベース Spear スコア(参考実装)
指標:
- Gap (40%): (Open - prev_Close) / prev_Close。1%ギャップアップ → スコア +1.0
- BullControl (35%): (Close - Low) / (High - Low)。終値が高値寄り = 買い圧力
- VolSpike (25%): Volume / 5日平均。出来高急増 = 勢いの裏付け
"""
OHLCV BT 結果¶
| シナリオ | モード | 閾値 | 総資産 |
|---|---|---|---|
| XS_OHLCV_T020 | ohlcv | 0.20 | $1,860K |
| XS_OHLCV_T025 | ohlcv | 0.25 | $1,862K |
| XS_OHLCV_T030 | ohlcv | 0.30 | $1,862K |
| XS_OHLCV_GV015 | ohlcv + GV015 | 0.25 | $1,912K |
結果: XS_Base($1,863K)と同等 → 改善なし
原因分析¶
OHLCV 式は「モメンタムが生じているかどうか」を Gap/BullControl で検知できる。 しかし GEX 谷条件(gex_valley=False)が依然として 32.7% のエントリーをブロックするため、 モメンタム側のスコア計算方式を変えても GEX 谷 bottleneck は解消されない。
BT 結果から見えた真実:
モメンタム問題(67.3%)→ threshold=0.40 で解決(ROC/RSI のまま)
GEX 谷問題(32.7%) → ratio_threshold=0.25 が正しい。緩和は逆効果
OHLCV 式は "解くべき問題が違った" 実験として記録
OHLCV 実装は残置
calculate_spear_momentum_ohlcv() は core/momentum.py に残置。
spear_momentum_mode="ohlcv" ScenarioConfig で将来の研究用に利用可能。
実運用への反映¶
XW ScenarioConfig (2026-03-02 更新)¶
# AEGIS/scripts/run_paper_trading_v3.py — XW シナリオ
spear_enabled=True, # 2026-03-02 有効化
spear_momentum_threshold=0.40, # BT 最適値 (0.40 > 0.5_default)
# spear_gex_valley_ratio は None = デフォルト 0.25 を維持
# spear_momentum_mode は "default" = ROC/RSI 式 (OHLCV 式は不採用)
評価ロジックの流れ¶
evaluate_regime() の Spear 判定:
1. is_gex_valley(gex_data, ratio_threshold=0.25) → bool
2. momentum_score = calculate_momentum_score(bars) # ROC/RSI/Vol
3. is_strong_momentum = abs(momentum_score) >= 0.40 # BT最適値
4. spear_score = 0.40 * is_strong_momentum
+ 0.40 * is_gex_valley
+ 0.10 * is_breakout_detected
+ 0.10 * is_gex_negative
5. Spear 発火条件: spear_score >= 0.50 AND is_bullish=True
期待されるエントリー件数の目安¶
| 条件 | 25ヶ月 BT 換算 |
|---|---|
| デフォルト設定 (t=0.5) | 57件 |
| threshold=0.40 (現行 PT) | 71件(+24%) |
| threshold=0.40 + GV015 | 69件 (DD 悪化のため不採用) |
BT 実行コマンド(再現用)¶
# XS 感度テスト(ベースライン vs 最適値)
python3 scripts/run_backtest_multiple_scenarios.py \
--scenarios XS_Base,XS_MT040 \
--start 2024-01-02 --end 2026-01-30 \
--deterministic --seed 0 --execution-model mid --monthly-withdrawal-rate 0.30 \
2>&1 | tee logs/bt_xs_mt040_$(date +%Y%m%d).log
# OHLCV 実験(参考)
python3 scripts/run_backtest_multiple_scenarios.py \
--scenarios XS_OHLCV_T020,XS_OHLCV_T025,XS_OHLCV_T030 \
--start 2024-01-02 --end 2026-01-30 \
--deterministic --seed 0 --execution-model mid --monthly-withdrawal-rate 0.30 \
2>&1 | tee logs/bt_xs_ohlcv_$(date +%Y%m%d).log
関連ファイル¶
| ファイル | 役割 |
|---|---|
core/momentum.py |
calculate_momentum_score(), calculate_spear_momentum_ohlcv() |
core/gex.py |
is_gex_valley() 実装 |
strategies/strategy_manager.py |
evaluate_regime() Spear 分岐 |
scripts/run_backtest_multiple_scenarios.py |
XS_MT040/OHLCV シナリオ定義 |
scripts/run_paper_trading_v3.py |
XW ScenarioConfig Spear 設定 |
更新履歴¶
| 日付 | 内容 |
|---|---|
| 2026-03-02 | Phase1 BT 完了、GEX Valley / モメンタム閾値 最適化確定。XW PT 適用。 |