A detector does not return one answer. It returns a pile of boxes, each with a confidence, and scoring that pile against the truth needs two decisions the lesson named: how much overlap counts as a hit, and how confident the detector must be before it is allowed to speak.
Turn the second dial up and the detector reports only what it is sure of — fewer boxes, more of them right. Turn it down and it catches more objects but reports more junk. There is no single correct setting, which is why detection results are reported as mAP, averaged across the whole curve rather than read at one setting. You are going to produce that curve.
Boxes are [x, y, w, h]: the top-left corner, then the width and height, with running right and running down. A prediction carries a fifth number, its confidence.
Task: write detection_scoreboard(truths, predictions, iou_threshold, confidence_levels), returning one [precision, recall] pair per confidence level, in the order given, each number rounded to 4 decimal places.
At each confidence level, score the detector like this:
iou_threshold, or every truth it overlaps is already claimed, it claims nothing. Ties in IoU go to the earlier truth in the list.
If the level filters away every prediction, the detector reported nothing and so got nothing wrong: report precision 1.0 and recall 0.0. There is always at least one truth box.
Step 3 is the whole problem. Consider one truth box [0, 0, 4, 4] and two predictions, [0, 0, 4, 4, 0.9] and [1, 0, 4, 4, 0.6], at iou_threshold = 0.5:
confidence_levels = [0.5, 0.8] the answer is therefore [[0.5, 1.0], [1.0, 1.0]]: at both boxes are reported and half are right; at the second is never reported and the detector looks perfect.That second row is the trade-off in miniature — the same detector, the same weights, a better-looking number, and not one extra object found.
A detector that reports every plausible box would have near-perfect recall and be useless. Precision alone is just as easy to fake by reporting almost nothing. Only the pair means anything, and only with the IoU threshold quoted alongside it.