DEV Community

Lucian (LKB)
Lucian (LKB)

Posted on • Originally published at lkforge.com

The BMI-to-body-fat gap is a constant 22.3 points at every BMI

BMI is one number: your weight divided by the square of your height. It has no term for age, no term for sex, no term for how much of your weight is muscle. So I got curious about a simple question while building a body-fat calculator:

If two people have the exact same BMI, how different can their body fat actually be?

The answer turned out cleaner than I expected — and it's a nice little demonstration of how a linear formula hides variance in plain sight.

The formula

The standard way to turn a BMI into a body-fat estimate is the Deurenberg equation. It's the "BMI method" our Body Fat Calculator ships:

const bodyFat = (bmi, age, isMale) =>
  1.20 * bmi + 0.23 * age - 10.8 * (isMale ? 1 : 0) - 5.4;
Enter fullscreen mode Exit fullscreen mode

Four terms. Only the first one involves BMI at all.

Four people, one BMI of 25

BMI 25 is the line where "normal" becomes "overweight." Let's put four people right on it and run the formula:

for (const [who, age, male] of [
  ['Man, 20',   20, true],
  ['Woman, 20', 20, false],
  ['Man, 70',   70, true],
  ['Woman, 70', 70, false],
]) {
  console.log(who.padEnd(10), bodyFat(25, age, male).toFixed(1) + '%');
}
// Man, 20    18.4%
// Woman, 20  29.2%
// Man, 70    29.9%
// Woman, 70  40.7%
Enter fullscreen mode Exit fullscreen mode

Same BMI. Same "overweight" label. Body fat from 18.4% to 40.7% — a 22.3-point spread. Run those through the ACE body-fat categories and two of them come out "Average" and two come out "Obese." One number, opposite verdicts.

The part I didn't expect: the gap never changes

Here's the neat bit. Because the sex term (-10.8) and the age term (0.23 * age) are added on independent of BMI, the distance between the leanest archetype (a 20-year-old man) and the highest (a 70-year-old woman) is a fixed amount at every BMI:

const low  = (bmi) => bodyFat(bmi, 20, true);   // leanest read
const high = (bmi) => bodyFat(bmi, 70, false);  // highest read

const gaps = new Set();
for (let bmi = 18.5; bmi <= 35; bmi += 0.5) {
  gaps.add(+(high(bmi) - low(bmi)).toFixed(1));
}
console.log([...gaps]); // [ 22.3 ]
Enter fullscreen mode Exit fullscreen mode

One distinct value: 22.3. The two body-fat-vs-BMI lines are perfectly parallel — a 22.3-point ribbon that just slides upward as BMI climbs. Decomposed:

  • Sex: a woman reads exactly 10.8 points higher than a man at the same BMI and age. It's a literal constant in the equation.
  • Age: 0.23 points per year, so 20 → 70 adds 11.5 points.
  • 10.8 + 11.5 = 22.3, forever.

So BMI can tell you where you land on the weight-for-height scale. It structurally cannot tell you which end of that 22.3-point band you're in — that information isn't in the inputs.

The honest caveat

The Deurenberg estimate is a rough BMI-based approximation, not a clinical measurement — the point here is how much a single BMI can hide, not a precise personal number. If you actually want a body-fat estimate, a tape-measure method (like the U.S. Navy girth formula) uses real body measurements and is meaningfully better. Both are in the calculator.

Full write-up with the chart and the category math: Same BMI, Different Body Fat →

Every number above is arithmetic on that one formula — copy the snippets and you'll get the same figures.

Top comments (0)