"""SKH_P_LOCAL_final — full study + causality + marginal on the top local-search winners, plus a small extra pass trying to push DD<35% while keeping minHold high (ptn45 + tighter exits).""" from __future__ import annotations import sys sys.path.insert(0, "/opt/docker/PythagorasGoal/scripts/research/skyhook") import skyhooklib as sk from src.strategies.skyhook import SkyhookParams V1 = dict(ptn_n=55, sl_atr=2.5, tp_atr=6.0, vola_lo=35.0, vola_hi=95.0, vol_lo=0.0) def evalp(**over): p = SkyhookParams(**{**V1, **over}) out = {a: sk.run_asset(a, p, fee_rt=sk.FEE_RT) for a in ("BTC","ETH")} return dict(over=over, min_full=min(out[a]["full"]["sharpe"] for a in out), min_hold=min(out[a]["holdout"]["sharpe"] for a in out), min_tr=min(out[a]["full"]["n_trades"] for a in out), max_dd=max(out[a]["full"]["maxdd"] for a in out)) # Small extra: ptn45 + tp7 + tighter SL or exit bars to chase DD<35 with hold>=0.5 print("=== extra DD-chase around ptn45 ===") for over in (dict(ptn_n=45, sl_atr=2.5, tp_atr=7.0, uscitalong=24, uscitashort=16), dict(ptn_n=45, sl_atr=2.25, tp_atr=7.0, uscitalong=24, uscitashort=16), dict(ptn_n=45, sl_atr=2.5, tp_atr=7.0, vola_lo=40.0), dict(ptn_n=45, sl_atr=2.5, tp_atr=8.0)): r=evalp(**over) print(f" {over} -> minFull={r['min_full']:+.2f} minHold={r['min_hold']:+.2f} maxDD={r['max_dd']*100:.0f}% minTr={r['min_tr']}") # WINNER candidates -> full study WINNERS = { "P_LOCAL_ptn45_sl2.5_tp7.0": dict(ptn_n=45, sl_atr=2.5, tp_atr=7.0), # best balanced (DD36, Full0.83, Hold0.69) "P_LOCAL_ptn45_sl2.25_tp7.0": dict(ptn_n=45, sl_atr=2.25, tp_atr=7.0), # best hold/clean-year (DD36, Hold0.77) } for name, over in WINNERS.items(): p = SkyhookParams(**{**V1, **over}) print(f"\n################ STUDY {name} over={over} ################") rep = sk.study(name, p) print(sk.fmt(rep)) print("causality:", sk.causality(p)) mg = sk.marginal(p) keys=("corr_full","corr_hold","marginal_verdict","has_insample_edge","is_hedge", "robust_oos","multicut_persistent","clean_year_uplift","jackknife_min_uplift", "cand_insample_sharpe","cand_full_sharpe") print("marginal:", {k: mg.get(k) for k in keys}) print("blend w25 uplift_hold:", mg.get("blends",{}).get("w25",{}).get("uplift_hold"), "uplift_full:", mg.get("blends",{}).get("w25",{}).get("uplift_full")) print("multicut:", mg.get("multicut_uplift")) print("AS_JSON:", sk.as_json(rep))