Sieben Verbesserungen umgesetzt: Breaker scharf, B5 entschieden, 5 Werkzeuge
1) CIRCUIT-BREAKER SCHARF -- daily_loss_limit_pct 0 -> 8. Live verifiziert:
enabled=True, limit_eur 89,44. Steht nicht in runtime_state.json, die ini
greift direkt. Begruendung: MaxDD 82,8 % auf dem gemessenen IST-Pfad,
schlechtester Einzeltrade -381 EUR.
2) B5-DEADLOCK RECHNERISCH AUFGELOEST -- die Regel ist ENTSCHIEDEN, nicht
vertagt. Stand 11/20: Verhaeltnis 0,14 (Latte 1,0), PF 0,39 (Latte 1,0).
Was die 9 Rest-Trades leisten muessten:
9/0 Gewinner -> 165,72 EUR je Trade = 12,2x der bisherige Schnitt
7/2 -> 186,17 EUR
5/4 -> 222,99 EUR
Der groesste Squeeze-Gewinn des Zeitraums war 77,34 EUR -- selbst der beste
Fall verlangt 2,1x den Rekord, neunmal in Folge. Latte nicht mehr erreichbar.
auto_squeeze bleibt FALSE. Wiederaufnahme waere eine NEUE Entscheidung mit
NEUER, vorab fixierter Latte.
3) core/kontrolle.py -- Kontroll-Fixture mit den Referenzwerten. Bricht bewusst
NICHT ab: ein Backtest darf abweichen, er muss es nur wissen und sagen.
4) core/live_config.py -- EINE Quelle der Live-Parameter (ini + runtime_state in
der Vorrangfolge des Engine-Starts). Dritte Instanz derselben Fehlerklasse:
ATRMIN_STD 0,12 statt 0,06, fehlendes set_entry_room, nachgebauter Cluster.
5) stichprobe.paarweise()/zeig_paarweise() -- gepaarter Vergleich. Anlass:
trail_start sah sequentiell besser aus, gepaart kippte das Vorzeichen
(Selektions- statt Exit-Effekt). Selbsttest in drei Richtungen bestanden.
6) tools/check_konstanten.py -- Waechter fuer veraltete Zahlen.
Erster Lauf: zwei Befunde, BEIDE Fehler in meiner eigenen Ableitung (Margin
aus Balance geschaetzt statt vom Broker gelesen; Elliott ohne
Gueltigkeitsfenster gezaehlt). Beide korrigiert.
Danach ein ECHTER Fund: meine am 13.08. notierten "~405 EUR/Lot" sind falsch,
der exakte Broker-Wert ist 712,84 -- die urspruenglich notierten 670 lagen
naeher als meine Korrektur. Lehre: eine abgeleitete Zahl ist keine gemessene.
Stand jetzt 0 Befunde.
7) Puls-Waechter bedingungs-bewusst: PULS traegt je Zeile die Vorbedingung,
bedingte Tabellen erscheinen als Hinweis statt als Ausfall. 0 Zeilen bleibt
IMMER ein Befund (der rec_outcomes-Fall). Grund: ein Waechter mit
Fehlalarmen wird ignoriert -- so ist der Divergenz-Waechter verstummt.
Pipeline gruen (85 Tests), Deployment ueber deploy.py --feld circuit_breaker
verifiziert, genau eine Instanz je Port.
Nicht angefasst: Sizing (User-Entscheidung) und die 44 Backtests mit eigener
Exit-Kopie (Migrations-Regel).
Co-Authored-By: Claude Opus 5 <noreply@anthropic.com>
This commit is contained in:
co-authored by
Claude Opus 5
parent
9dbc5d0452
commit
792355e8f9
@@ -123,3 +123,49 @@ def schluessel_level_stunde(level_feld="level", ts_feld="ts"):
|
||||
ts = _feld(z, ts_feld)
|
||||
return (round(float(lvl or 0), 2), int(ts or 0) // 3600)
|
||||
return f
|
||||
|
||||
|
||||
def paarweise(basis: dict, variante: dict, wiederholungen: int = 3000,
|
||||
seed: int = 7):
|
||||
"""GEPAARTER Vergleich zweier Exit-/Regel-Varianten auf DENSELBEN Faellen.
|
||||
|
||||
⚠⚠ WARUM DAS NOETIG IST (2026-08-14, real passiert). Beim `trail_start`-Sweep
|
||||
sahen SEQUENTIELL vier Werte in beiden Haelften besser aus (Δ bis +0,101).
|
||||
Gepaart kippte in H2 das Vorzeichen. Ursache: eine sequentielle Sim mit EINEM
|
||||
Positions-Slot nimmt bei anderem Exit ANDERE Trades — der scheinbare Gewinn
|
||||
war ein **Selektionseffekt**, kein Exit-Effekt. Dieselbe Falle steckte am
|
||||
31.07. in `backtest_exit_combo.py` („verschiedene Trade-Folgen sind nicht
|
||||
vergleichbar").
|
||||
|
||||
⚠ Und der gepaarte Test ist nicht nur richtiger, sondern **trennschaerfer**:
|
||||
die Einzel-Intervalle messen die Streuung der TRADES, das gepaarte die des
|
||||
UNTERSCHIEDS — und die ist um ein Vielfaches kleiner.
|
||||
|
||||
`basis` / `variante`: {schluessel: ergebnis}. Der Schluessel identifiziert den
|
||||
Fall (z. B. der Einstiegs-Bar-Index). Verglichen wird nur die Schnittmenge.
|
||||
|
||||
Rueckgabe: (mittlere Differenz, lo, hi, n) — bei n < 20 (None, None, None, n).
|
||||
"""
|
||||
import random as _r
|
||||
gemeinsam = [k for k in basis if k in variante]
|
||||
dif = [variante[k] - basis[k] for k in gemeinsam]
|
||||
n = len(dif)
|
||||
if n < 20:
|
||||
return None, None, None, n
|
||||
m = sum(dif) / n
|
||||
r = _r.Random(seed)
|
||||
bs = sorted(sum(dif[r.randrange(n)] for _ in range(n)) / n
|
||||
for _ in range(wiederholungen))
|
||||
return m, bs[int(.025 * wiederholungen)], bs[int(.975 * wiederholungen)], n
|
||||
|
||||
|
||||
def zeig_paarweise(name: str, basis: dict, variante: dict) -> bool:
|
||||
"""Druckt den gepaarten Vergleich und sagt, ob er die Null ausschliesst."""
|
||||
m, lo, hi, n = paarweise(basis, variante)
|
||||
if m is None:
|
||||
print(f" {name:<28} zu wenige gemeinsame Faelle (n={n})")
|
||||
return False
|
||||
ok = lo > 0 or hi < 0
|
||||
print(f" {name:<28} Δ je Fall {m:>+.4f} KI [{lo:+.4f} … {hi:+.4f}] "
|
||||
f"n={n} {'✅ ohne 0' if ok else '⚠ enthaelt 0'}")
|
||||
return ok
|
||||
|
||||
Reference in New Issue
Block a user