Field note · March 26, 2024
first_response_min by priority: a 1,095% spread
Real group means for one column across 4 segments, and what the pooled average conceals.
Breaking first_response_min down by priority on support-tickets, because the headline average is 155 and no segment is actually there.
low— mean 290, median 172 (864 rows)normal— mean 143, median 95 (1,935 rows)high— mean 67, median 41 (903 rows)urgent— mean 24, median 18 (298 rows)
Top to bottom that is 290 against 24, a spread of 1,094.9%. The pooled average is 155.
select priority,
count(*) as rows,
round(avg(first_response_min)::numeric, 2) as mean,
percentile_cont(0.5) within group (order by first_response_min) as median
from support_tickets
group by 1
order by mean desc;A spread that wide means the pooled number is not a summary, it is an artefact of the mix. Change the proportion of low rows and the overall average moves without any individual group changing at all — which is how a metric goes up while every segment goes down.
Notice the mean and median columns disagree most in low, where the mean sits well above the median. Always compute both in the group-by. The comparison between them per segment is free and tells you whether you are looking at a level difference or a tail difference.
This is the setup for Simpson's paradox — the case where every segment moves one way and the total moves the other.