Method
A plain model, checked against the market in public
The model adds up a handful of points terms into a predicted margin, then turns that margin into a chance to win. Over six seasons it picked 65.4% of winners. The betting market picked 67.9%. It does not beat the market, and this site never says it does.
What goes into a call
For each game the model estimates the home team's margin from five terms, all in points:
- Team rating: the gap between the two teams' current strength, updated after every game and pulled halfway back to average between seasons.
- Home court: the recent value of playing at home, measured over the last 1,230 games.
- Rest, travel and altitude: small adjustments for back-to-backs, distance flown and playing in Denver or Utah.
The margin becomes a win chance through a normal curve with a spread of 12.8 points. The day page for each slate shows every term for every game, next to the log line the model wrote.
What it does not know
The model does not know injuries, rest days for stars, or starting lineups. The market does, right up to tip-off. When a star sits, the market moves and the model does not. That gap is most of the reason the market is ahead, and it is the obvious next thing to add.
The backtest
Walk-forward over 2020-21 to 2025-26: each game was predicted using only what was known before it, then compared with the closing betting line. 7,227 games had a closing line.
| Line | Picked the winner | Brier score | Log loss |
|---|---|---|---|
| Model | 65.4% | 0.2158 | 0.6205 |
| Closing market | 67.9% | 0.2052 | 0.5960 |
Lower is better for Brier score and log loss; both measure how good the stated chances were, not just the picks.
- The market was ahead in every one of the six seasons, by 0.9 to 3.6 points of accuracy.
- In the 2,372 games where the two disagreed (a different winner, or margins at least 10 points apart), the model was right 58.5% of the time and the market 65.9%.
- Against the closing spread, the result landed on the model's side in 50.0% of 7,166 games. That is a coin flip: no edge.
The fair summary: within about 2.5 points of the closing market, from free data, before tip-off.
Reading the live record
Early in a season the live record is a small sample. Ten games can read 80% or 40% by luck alone. Under 100 graded games the home page says so next to the numbers, and the backtest above is the better guide to what the model can do.
How to verify a call
Clone the repository with its full history.
git clone https://github.com/AmeyaMprojects/nba-predictor.git cd nba-predictorSee which commit added each prediction line, and when.
git blame --date=iso predictions/2026-27.jsonlRead the commit itself, with its time and the lines it added.
git show --stat 5a16664 git log --format='%h %ci %s' -- predictions/Or open any commit on GitHub. Every hash on this site links to
github.com/followed by the hash.AmeyaMprojects/ nba-predictor/ commit/
Compare the commit time with the game's tip-off time on the same line. A commit time is set by the machine that made it, which is why the public history matters: once pushed, a rewrite would no longer match the copies other people already pulled.
Not betting advice
This is a public record of a model's calls, kept to see how close free data can get to the market. It is not a tip sheet. Nothing here says to bet on anything.