Data Science
Model Lab
The machinery behind the predictions, made playable. Every visual recomputes live in your browser from the real engine — drag a control and watch the math move. No black boxes: a bivariate-Poisson goals model, a Monte Carlo tournament simulator, PCA + k-means on team style, model calibration, and Shapley attribution.
Bivariate-Poisson Score Matrix
The generative model behind every prediction
Each prediction starts here: two goal expectations (λ) feed a bivariate-Poisson distribution over every possible scoreline, with a shared component (λ₃) for the correlation between the two scores. Win/draw/loss, BTTS and over/under are just sums over this grid. Load a real fixture or drag the λ sliders to reshape it.
Match outcome
Most likely scores
- 1–111.9%
- 1–09.3%
- 2–18.9%
- 0–17.9%
- 1–27.5%
Monte Carlo What-If Simulator
Re-run the tournament 3,000 times with a team's strength of your choosing
Override a team’s attack, defense or ELO and the real engine re-simulates the rest of the tournament 3,000 times against the current results — sampling every remaining group game, resolving the bracket, and playing it out. Watch the chosen team’s survival path and the whole title race react.
🇪🇸 Spain — survival path
Title-odds leaderboard
Running the first simulation…
Monte Carlo Convergence
The law of large numbers, watched live
The same bivariate-Poisson model, two ways. We sample random scorelines one batch at a time and tally win/draw/loss — the solid lines are that running estimate, the dashed lines the model’s exact answer. The estimate wobbles wildly at first, then homes in: the error shrinks with 1/√n. This is exactly how the tournament simulator works, just on one match.
Solid = the running Monte Carlo estimate from sampled scorelines; dashed = the exact bivariate-Poisson probability. Watch the estimate converge as n grows — the shaded band is ±2 standard errors (∝ 1/√n).
Live Win-Probability Timeline
The model re-read minute-by-minute from the event feed
For any played match, the win probability is rebuilt at every minute from the score so far and the goals still expected in the time remaining — so each goal visibly swings it, and a sending-off bends the curve. Pre-match prediction at kickoff, the actual result by full time.
Win probability rebuilt minute-by-minute from the event feed: the model re-reads the match at each minute from the live score and the goal expectation left in the remaining time (red cards cut a side’s rate). Hover to scrub. ⚽ = goal, pink bar = red card.
At kickoff this is the pre-match prediction; by full time it resolves to the result. The jumps are goals — each one swings the model.
Team Embedding — PCA + k-means
48 teams, 8 style dimensions, projected to 2D
Every team is a vector of playing-style metrics. Principal Component Analysis (computed in-browser via a covariance eigendecomposition) collapses that to two axes that capture the most variance, and k-means groups teams into stylistic clusters. Toggle which metrics feed the projection and it recomputes instantly.
Metrics in the projection
Colour by
Feature Relationships & Model Fit
How the metrics move together, and where the goals model misses
Left: the Pearson correlation matrix across the team-style metrics — which qualities travel together (attack and xG) and which trade off. Right: a residual plot of predicted (xG-rate) goals versus what teams actually scored, with the mean absolute error and bias — the honest view of how well the model tracks reality.
Metric correlation matrix · across 48 teams
Pearson r between every pair of team-style metrics (teal = move together, pink = inversely). Computed in-browser.
Model fit · predicted vs actual goals
Points above the dashed line scored more than the model expected. Positive bias = teams out-scoring their xG-rate so far.
Calibration Lab
Is the model honest? Predicted probability vs observed frequency
A reliability diagram tests whether stated probabilities mean what they say — of all the times the model said 70%, did it happen ~70% of the time? The Brier score and its Murphy decomposition (reliability − resolution + uncertainty) quantify it against every finished match.
Points on the dashed line = perfectly calibrated. Bubble size = sample in that bin.
Murphy decomposition: Brier = Reliability − Resolution + Uncertainty. Low reliability means the stated probabilities match reality; high resolution means the model separates likely from unlikely. Hit rate 66% across 104 matches.
Outcome class
Prediction Explainer — Shapley values
What drives a single match prediction
Game-theoretic attribution: each input (home advantage, both teams’ attack and defense) gets credit equal to its average marginal effect over every ordering — exact Shapley values. The contributions sum precisely from the neutral baseline to the model’s win probability.
Each bar is a factor’s exact Shapley contribution to the home-win probability — its average marginal effect over every ordering of the inputs. Green pushes the home win up, red pulls it down. They sum to the model output.