ggplot中geom_bar的stat=identity参数含义及代码疑问
Hey there! Let's unpack this confusion step by step—your observations are totally on point, and I’ll break down exactly what’s happening with that code, plus clarify what stat="identity" actually does.
First, what your current code is doing
Your guess is correct: this code is drawing a bar for every single row in your dataset, not aggregating values for Group A and B. Here’s why:
- When you set
stat="identity"ingeom_bar(), you’re telling ggplot: "Don’t calculate any new values for the y-axis—use the exact numbers from myValuecolumn as the height of each bar." - Your data has multiple rows for Group A and Group B (e.g., two A rows with values 20 and 24, two B rows with 74 and 50). Since all these rows share the same
x=Groupvalue (A or B), their bars get drawn in the same position. - You added
position="dodge", but since yourfillis also mapped toGroup, ggplot doesn’t see a reason to dodge the bars (they’re all part of the same fill group). So the bars stack/overlap instead of side-by-side. The tallest bar in each group ends up on top, making it look like only the maximum value is displayed.
What stat="identity" really means
To put it simply:
- The default behavior of
geom_bar()(without specifyingstat) isstat="count": it counts how many times eachxcategory appears, and uses that count as the bar height (noyvariable needed). stat="identity"overrides this—it tells ggplot to use your providedyvalues directly. This is useful when you’ve already pre-calculated aggregated values (like sums, means, or medians) and just want to plot them as bars.
How to fix it to plot aggregated stats (like mean/median)
Your hunch that the original goal was to plot summary statistics is spot-on. There are two easy ways to do this:
1. Pre-aggregate your data first (using dplyr)
Calculate the summary statistic you want (e.g., mean) before plotting:
library(dplyr) # Calculate mean Value for each Group summary_data <- data %>% group_by(Group) %>% summarize(Average_Value = mean(Value)) # Now plot the aggregated data ggplot(summary_data, aes(x = Group, y = Average_Value, fill = Group)) + geom_bar(stat="identity", position = "dodge", lwd = 1)
2. Let ggplot handle the aggregation (using stat_summary)
You can skip pre-aggregating and have ggplot calculate the summary on the fly:
ggplot(data, aes(x = Group, y = Value, fill = Group)) + stat_summary(fun = mean, geom = "bar", position = "dodge", lwd = 1)
Replace fun = mean with fun = median or fun = sum if you want a different summary statistic.
内容的提问来源于stack exchange,提问作者Agustin

