Calibrating Image Classifier Confidence Scores
10 min read · updated August 11, 2026
A softmax output is a number between 0 and 1 that people read as a probability. It is not one by construction, and on a modern image classifier it is usually wrong in a specific direction: too high.
The number that is not a probability
The softmax normalises a vector of logits to sum to 1. That gives you something with the arithmetic shape of a distribution, and nothing in the training objective ever required it to match observed frequencies. Cross-entropy is minimised by pushing the correct class’s logit up without bound, so a network that has fit its training set drives its outputs toward one, and it keeps doing so on inputs it should be unsure about.
A model is calibrated if, across all the cases where it said 0.8, it is right 80% of the time. That property is what makes a confidence usable as an input to a decision — routing to a human reviewer, choosing an operating threshold, or combining with another signal. Without it a threshold is a magic number that has to be re-tuned every time anything changes, which is precisely the situation most production classifiers are in.
A reliability table, and ECE computed from it
The measurement is straightforward. Take a held-out set, bin the predictions by their top-class confidence, and in each bin compare the mean confidence with the observed accuracy. Here are 1,000 held-out predictions from a five-class classifier, in five bins:
bin n mean conf accuracy gap
[0.5,0.6) 60 0.55 0.52 0.03
[0.6,0.7) 90 0.65 0.58 0.07
[0.7,0.8) 140 0.75 0.64 0.11
[0.8,0.9) 260 0.85 0.71 0.14
[0.9,1.0] 450 0.96 0.83 0.13
----
1000
ECE = sum over bins of (n/N) * |accuracy - confidence|
= 0.06*0.03 + 0.09*0.07 + 0.14*0.11 + 0.26*0.14 + 0.45*0.13
= 0.0018 + 0.0063 + 0.0154 + 0.0364 + 0.0585
= 0.118
overall accuracy = 731 / 1000 = 0.731
mean confidence = = 0.850A reliability diagram is this table drawn as a bar chart with accuracy against confidence; perfect calibration is the diagonal, and every bar here sits below it. The model is 73.1% accurate and believes itself to be 85.0% accurate. Read the top bin concretely: of the 450 predictions made at an average confidence of 0.96, 77 were wrong. If your human-review rule was “send anything under 0.9 to a reviewer”, those 77 errors went through unreviewed at what looked like near-certainty.
Two properties of ECE are worth knowing before you quote one. It depends on the bin count — more bins generally report a larger error, so an ECE without its binning scheme is not comparable to another. And it is computed on the top class only, so a model can have a low top-label ECE and badly wrong probabilities for every other class; where the full distribution matters, class-wise ECE or the Brier score is the better instrument.
Why modern networks are overconfident
This is not folklore. Guo, Pleiss, Sun and Weinberger documented it directly in “On Calibration of Modern Neural Networks” (2017), showing that the deep networks of that era were substantially less calibrated than the shallower models that preceded them despite being more accurate, and identifying increased capacity and the reduction of weight decay as contributing factors, with batch normalisation implicated as well.
The mechanism is easy to state. Once a network can fit its training set to near-zero error, continued training cannot improve accuracy and can still reduce loss — by making the already-correct predictions more confident. Every epoch after convergence is spent inflating confidence. Regularisation that limits how far the logits can grow, such as weight decay or label smoothing, mitigates it; removing that regularisation to chase a fraction of a point of accuracy makes it worse.
Temperature scaling, worked
The standard fix is one parameter. Divide the logits by a scalar T before the softmax, and fit T by minimising negative log-likelihood on a validation set the model was not trained on. That is the whole method:
logits z = (4.0, 2.0, 1.0) T = 1 exp(4.0)=54.598 exp(2.0)=7.389 exp(1.0)=2.718 sum = 64.705 p = (0.844, 0.114, 0.042) T = 2 z/T = (2.0, 1.0, 0.5) exp(2.0)= 7.389 exp(1.0)=2.718 exp(0.5)=1.649 sum = 11.756 p = (0.629, 0.231, 0.140) argmax unchanged -> accuracy unchanged top confidence -> 0.844 becomes 0.629
The property that makes this safe to deploy is in the last two lines. Dividing every logit by the same positive constant cannot change which logit is largest, so temperature scaling changes no prediction and no accuracy, no precision and no recall. It only changes the number attached to them. That also means it cannot fix a model that is wrong; it fixes a model that is right about ranking and wrong about certainty.
Fit it on a held-out split, never on training data — a model that has memorised its training set will fit T near 1 and learn nothing. Values above 1 soften an overconfident model, which is the common case; a fitted T below 1 means your model is underconfident, which usually indicates heavy label smoothing or a mislabelled validation split rather than a real finding.
What calibration does not survive
Temperature scaling calibrates a model on the distribution it was calibrated on. Ovadia and colleagues examined this directly in “Can You Trust Your Model’s Uncertainty?” (2019), finding that calibration achieved on in-distribution data degrades as the test distribution shifts, and that post-hoc methods fitted on a clean validation set do not hold up under that shift.
For a deployed vision system that is the normal condition rather than an edge case. A new camera, a new lens, a firmware change to the sensor, a seasonal change in daylight — each moves the input distribution, and the confidences move with it while the calibration constant stays where you left it. Two consequences follow. First, calibration is a maintenance task with a schedule, not a one-off; hold back a labelled sample from live traffic and refit periodically. Second, a single global T is an average over subpopulations, so a model can be well calibrated overall and badly calibrated for one camera or one product line. If a subgroup matters, measure ECE for that subgroup separately — the aggregate will not show it, which is a specific case of the general gap between validation and production behaviour.
Using a calibrated score
Once the score means something, the threshold can be derived rather than guessed. If accepting a wrong prediction costs C_error and sending a case for human review costs C_review, then reviewing a case is worth it whenever the probability of error exceeds C_review / C_error — so the confidence threshold is 1 - (C_review / C_error). With review at 12 and an error at 900, that is a threshold of 0.987: anything the model is less than 98.7% sure about goes to a human. The same arithmetic drives the operating point in manufacturing defect detection, and it is only valid if the score is calibrated, because it treats the confidence as a probability.
One caution on abstention: a calibrated confidence tells you about uncertainty within the classes the model knows. An input from a class it has never seen can produce a confident, calibrated-looking, entirely wrong answer, because the softmax is a distribution over the classes you gave it and nothing else. That is an out-of-distribution detection problem and it needs its own mechanism — a distance in feature space, an energy score, or an explicit reject class — not a better temperature.