Choosing and changing models
By the end: You can pick a model for a task with evidence, and survive the model being retired.
- Why benchmarks do not answer your question
- Running your own comparison
- The dimensions besides quality
- Models get retired, and what that means for your code
New to choosing a model? Several providers offer dozens of models at prices that differ by more than a hundredfold, and they do not form a single ranking: the best one for summarising support tickets need not be the best one for writing code. Choosing means running your own task across the candidates and comparing quality, cost and speed on your own examples. It is a decision you revisit, because new models arrive constantly and old ones are withdrawn. Why it matters
Choosing a model looks like a research problem and is really a measurement problem. The leaderboards cannot answer it, because they measure a different task on different data from yours, and the differences between the top few are usually smaller than the uncertainty on your own evaluation. This section is about running the comparison that does answer it: what to measure, how many examples you actually need before the answer means anything, the dimensions besides quality that decide it in practice, and what to do about the fact that the model you choose will be retired.
Why benchmarks do not answer your question#
A public benchmark is a real measurement of something, and that something is not your product. Three gaps separate the two, and each is large on its own. The task is different — a score on graduate-level physics questions predicts very little about extracting fields from your invoices. The data is different, and for anything published before a model was trained there is a genuine chance the test set is in the training data, which the model's own report will usually acknowledge if you look. And the prompt is different: benchmark harnesses use their own formatting and few-shot examples, so the number describes a setup you are not running.
The practical consequence is not that benchmarks are useless, but that they are a shortlist rather than a decision. Use them to pick three candidates and to rule out the ones that are clearly a tier below. Then measure the three on your own task, because that measurement is cheap — usually an afternoon — and it is the only one that describes what you are about to ship.
How many examples you need#
Before building an eval set it is worth knowing how large it has to be, because the intuitive answer is far too small. Here two models differ in the realistic way: the newer one fixes some of the older one's mistakes and breaks a few of its correct answers. Both answer the same examples, so the comparison is paired, which is the strongest test available.
import numpy as np
rng = np.random.default_rng(0)
def called_correctly(n, fix, brk, trials=2000, base=0.70):
"""B fixes that fraction of A's errors and breaks that fraction of its
correct answers. Returns how often n examples declare B the better model."""
hits = 0
for _ in range(trials):
a = rng.random(n) < base
b = a.copy()
b[~a & (rng.random(n) < fix)] = True # fixes
b[ a & (rng.random(n) < brk)] = False # regressions
d = b.astype(int) - a.astype(int)
sd = d.std(ddof=1)
if sd == 0:
hits += d.mean() > 0
continue
hits += (d.mean() / (sd / np.sqrt(n))) > 1.96 # paired t
return hits / trials
for n in (50, 100, 200, 500, 1000):
print(n, round(called_correctly(n, 0.20, 0.02) * 100, 1))
# a true gap of 4.6 points
# 50 20.5 % of the time
# 100 37.8
# 200 69.6
# 500 97.7
# 1000 100.0Run it again with a smaller difference and the conclusion sharpens. A model that fixes ten per cent of errors while breaking three per cent of correct answers is genuinely better by 0.9 points, and two thousand examples still only calls it correctly 44 per cent of the time. A difference that small is not measurable at any eval-set size you are going to build, which is the useful thing to know: stop trying to resolve it and choose on cost, latency or something else that is measurable.
What this means for your eval set
Aim for two hundred to five hundred examples that look like real traffic, and expect to resolve differences of roughly five points and not much finer. Add examples from production failures as they appear, since those are worth more per item than anything you invent. And when two models land within a point of each other, treat that as a tie rather than a ranking — it is the honest reading, and it frees the decision to be made on the dimensions below.
Running your own comparison#
The comparison itself is deliberately unglamorous, and the discipline is in holding everything else constant.
- 1.Take two to five hundred real inputs, including the awkward ones. Sampled production traffic beats anything written from imagination.
- 2.Fix the prompt, the temperature and the output format, and change only the model between runs.
- 3.Score with whatever you already trust: exact match where the task allows it, a validated judge where it does not, and human review of the disagreements.
- 4.Report the paired difference with an interval, not two separate averages.
- 5.Read the examples where they differ. That set is small, and it tells you more about which to ship than the aggregate does.
Step five is the one people skip and the one that pays. The aggregate says which model is better on average; the disagreements say whether the newer model is better in the way you need, or merely better at the parts of your traffic you care least about.
The dimensions besides quality#
Quality is one column of the decision and rarely the deciding one, because the top models are usually close enough that the eval cannot separate them. The others are measurable in an afternoon and differ by much more than a few points.
dimension how to measure it why it decides
cost per request tokens in and out x rate scales with every user
latency, p95 your prompts, your region p50 hides the problem
context window does your input fit a hard limit, not a preference
structured output does it honour a schema removes a whole class of parsing
tool calling reliability on your tools agents live or die on this
rate limits requests and tokens/min the launch-day constraint
data handling retention and training use sometimes decides it outright
deprecation history how long models have lasted how often you will redo thisModels get retired#
Every model you choose will be deprecated, usually with months rather than years of notice, and the code that assumed otherwise is the code that breaks. Treat the model as a configured dependency rather than a fact of the system: one place in the codebase names it, the name is pinned to a specific version rather than a floating alias, and the eval set can be run against a new one on an afternoon's notice.
That last point is the real defence. A team with a two-hundred-example eval set treats a deprecation as a scheduled task: run the eval against the replacement, read the disagreements, adjust the prompt, ship. A team without one treats it as a crisis, because they have no way to tell whether the new model is worse until users tell them. The eval set you build to choose a model is the same artefact that makes changing it routine, which is the argument for building it properly the first time. The mechanics of the change itself are the next section.
Where people go wrong
Choosing on leaderboard position. Benchmarks leak into training data and do not resemble your task, so a high score can mean memorisation rather than capability on the thing you care about.
If this comes up in an interview
How would you choose between two models?
Use benchmarks only to shortlist, then run my own eval on real tasks and compare pass rate, cost and p95 latency together. Keep the prompt identical for the first comparison, then tune per model, since the ranking can change once each gets a fair prompt.
Then they push further
The cheaper model scores 3 points lower on your eval. Which do you pick?
Check first that 3 points is not noise. Then look at which cases it fails and what those failures cost. If they are low stakes and the saving is large, route those requests to the cheaper model. If they include costly errors, the saving is not worth it.
What gets marked up. Marked up for deciding on your own eval, cost and latency rather than public benchmarks, and for looking at which cases differ, not just the totals.
A provider is deprecating the model you use. What do you do?
The identifier should already be in configuration in one place, so the change is one line. Then re-run the eval before switching, because a newer model is not automatically better on a specific task and its failure cases move.
Why not always use the most capable model?
Cost and latency, and often neither is justified. Most workloads are mostly easy, so routing the easy majority to a smaller model and escalating the rest usually holds quality at a fraction of the spend. That claim needs an eval behind it.
Build this: Run the same twenty-task eval across three models and report pass rate, cost and p95 latency for each. Then tune the prompt for the weakest one and see whether the ranking changes.
Watch it explained
This is one section of Choosing a model, 10 hours across 2 sections. Read it in full to get the whole topic in order.
Stop 45 of 50 on the AI Engineer route
0 of 50 topics done · 0h behind you, 603h to go
What you have marked done is stored in this browser only. It does not reach a server, and clearing site data will clear it.