如何用ggplot2自定义条形图填充比例并添加X轴计数标注?
解决方案
1. 按指定比例绘制堆叠条形图
首先需要把宽格式数据转换为长格式,让ggplot能识别分组填充逻辑。用tidyr::pivot_longer将g1、g2、g3列转为分组和对应比例,再计算每个分组的实际outcome数值(比例×总outcome):
library(tidyverse) # 数据格式转换:宽转长 + 计算分组对应结果值 df_long <- df %>% pivot_longer(cols = starts_with("g"), names_to = "group", values_to = "proportion") %>% mutate(group_outcome = outcome * proportion) # 绘制堆叠条形图 ggplot(df_long, aes(x = age_group, y = group_outcome, fill = group)) + geom_col() + labs(y = "outcome", fill = "分组")
geom_col默认使用position = "stack",会自动按比例堆叠各分组的条形高度,完全匹配g1/g2/g3的比例要求。
2. 在X轴下方添加count值
用geom_text在X轴对应位置下方添加count数值,通过设置y轴负坐标让文本显示在条形下方,同时调整轴范围避免文本被截断:
ggplot(df_long, aes(x = age_group, y = group_outcome, fill = group)) + geom_col() + # 添加count文本到X轴下方 geom_text(data = df, aes(x = age_group, y = -5, label = paste("count:", count)), color = "dimgray", size = 3.5) + # 扩展Y轴范围,避免文本被截断 expand_limits(y = -10) + labs(x = "年龄组", y = "outcome", fill = "分组") + # 调整X轴标签与文本的间距 theme(axis.text.x = element_text(margin = margin(t = 8)))
完整整合代码
library(tidyverse) df <- tribble( ~age_group, ~count, ~outcome, ~g1, ~g2, ~g3, "first", 10, 110, 0.3, 0.6, 0.1, "second", 20, 70, 0.4, 0.3, 0.3, "third", 80, 35, 0.25, 0.5, 0.25 ) df_long <- df %>% pivot_longer(cols = starts_with("g"), names_to = "group", values_to = "proportion") %>% mutate(group_outcome = outcome * proportion) ggplot(df_long, aes(x = age_group, y = group_outcome, fill = group)) + geom_col() + geom_text(data = df, aes(x = age_group, y = -5, label = paste("count:", count)), color = "dimgray", size = 3.5) + expand_limits(y = -10) + labs(x = "年龄组", y = "结果值", fill = "分组") + theme(axis.text.x = element_text(margin = margin(t = 8)))
最终图表会呈现:每个年龄组的条形按g1/g2/g3比例堆叠填充,X轴下方对应显示该组的count数值。
内容的提问来源于stack exchange,提问作者dcsuka
相关产品推荐
相关产品推荐

