Mt5pro-bot2/python/backtest/montecarlo.py

21 lines
1.1 KiB
Python

import numpy as np
def monte_carlo(trades, initial, runs=2000, ruin_dd_pct=30.0, seed=42):
"""Rééchantillonne les trades (rendement par trade, composé) pour estimer la dispersion des résultats."""
if len(trades) < 10:
return None
rets = (trades.pnl / trades.equity_before).to_numpy()
rng = np.random.default_rng(seed)
idx = rng.integers(0, len(rets), size=(runs, len(rets)))
paths = initial * np.cumprod(1 + rets[idx], axis=1)
paths = np.concatenate([np.full((runs, 1), initial), paths], axis=1)
peak = np.maximum.accumulate(paths, axis=1)
dd = ((peak - paths) / peak).max(axis=1) * 100
final = paths[:, -1]
q = lambda x, p: float(np.percentile(x, p))
return {"runs": runs, "trades": len(rets),
"final_p5": q(final, 5), "final_p50": q(final, 50), "final_p95": q(final, 95),
"dd_p50": q(dd, 50), "dd_p95": q(dd, 95),
"prob_loss": float((final < initial).mean() * 100),
"prob_dd10": float((dd >= 10).mean() * 100),
"prob_ruin": float((dd >= ruin_dd_pct).mean() * 100), "ruin_dd_pct": ruin_dd_pct}