Teaching an AI to say “none of the above”
My wildlife app’s model was right 98.9% of the time and still couldn’t admit when it didn’t know. The fix was already sitting in results I’d saved.
In one of my test photos, an opossum came back as a raccoon. With confidence.
The model behind my wildlife discovery app names the animals you photograph, and on the 40 species it knows, it’s right 98.9% of the time. That’s the good news. The bad news showed up when I tested it on animals it doesn’t know, because a trustworthy app has to be able to say “Not sure.”
The setup
My test has 763 photos: 632 of the 40 species the app knows, and 131 of animals that aren’t on the list (relatives of those species, wildlife from other states, pets). I’ll call those the strangers, because the right answer for them is “none of these.” For my first attempt, I used the model’s own confidence. If it wasn’t confident enough, the app would say “Not sure.”
It caught 82.4% of the strangers. It also sent 5.9% of the animals it did know to “Not sure,” which is a lot of doubt about answers that were mostly right. And the strangers that got through were funny in a way that told me something. A different kind of rabbit became Desert Cottontail. Two red dragonflies became Flame Skimmer. A Black-chinned Hummingbird became an Anna’s. A deer became a different deer, and an opossum became a raccoon.
Why the model can’t say it
The model scores a photo against all 40 species, and those scores always add up to 100%. That’s a softmax, and it’s a multiple-choice test with no “none of the above.” Hand it a rabbit that isn’t on the list and it still has to hand out its 100%. Desert Cottontail wins, even though it’s a poor match, because the other 39 are even worse.
So the model wasn’t wrong, exactly. I’d asked it a bad question. I’d asked “which of these 40 is it most like?” when I needed “is it like any of them?”
The dead end
I’d already hit the same wall from the other side with a general-purpose AI model I tried as an alternative. Its confidence was bunched into a narrow range, so I tried tuning the cutoff. That went nowhere. Nudging it from 85 to 86.5 pushed the share of strangers caught from 79% up to 89%, which sounds great. It also pushed the share of listed animals sent to “Not sure” from 30% up to 49%. No setting gave me both.
The fix was already in the data
Underneath the percentages, the model produces a raw similarity score for each species. It measures how closely the photo matches that species, with no competition from the other 39. Take the best score, and it tells you whether the photo looks like anything on the list at all. The rabbit stays unconvincing even when its percentage looks great.
I tried it on the results I’d already saved, so there were no new runs and no new photos. Every one of the 632 photos of listed species scored above my cutoff, right or wrong. And 88.5% of the strangers fell below it. Zero animals on the list sent to “Not sure,” versus 5.9% before.
The caveats
I tuned the cutoff on just 57 stranger photos, so it’s coarse, and the test photos only cover July through October. About 1 in 9 of the strangers still slips through as a confident match, and they’re all close relatives of a listed animal. Telling them apart takes a second opinion, which is a story for the project page and, eventually, another post.
The takeaway
A confidence score only means what it was built to separate. The percentages looked like certainty, but they were really measuring “better than the other 39.” Before building on a score, look at what it actually separates, and see what the data you already have can tell you.