You need to enable JavaScript to run this app.
优惠活动
大模型
产品
解决方案
定价
更多

在R中如何从另一个DataFrame向堆叠柱状图添加顶部geom_text

解决ggplot2堆叠柱状图顶部添加跨数据集百分比文本的问题

核心思路

要在堆叠柱状图顶部显示来自另一数据集的百分比,关键是让文本数据集的行数与x轴分组数(月份)完全匹配,同时将文本的y值设为对应月份堆叠柱的总高度。

完整示例代码

先模拟测试数据,再给出绘图代码:

# 加载所需包
library(ggplot2)
library(dplyr)

# 模拟sum_slaughter_2021数据集(月份、类别、屠宰总量)
sum_slaughter_2021 <- tibble(
  month = rep(1:12, each = 3),
  kind = rep(c("牛", "猪", "羊"), 12),
  total_slaughter = sample(100:500, 36, replace = TRUE)
)

# 模拟month_rate_2021数据集(月份、月度比率)
month_rate_2021 <- tibble(
  month = 1:12,
  month_rate = runif(12, 0.1, 0.5)
)

# 1. 预处理文本数据:计算每个月份的堆叠柱总高度,并与月度比率合并
text_data <- sum_slaughter_2021 %>%
  group_by(month) %>%
  summarise(total_height = sum(total_slaughter), .groups = "drop") %>%
  left_join(month_rate_2021, by = "month")

# 2. 绘制堆叠柱状图+顶部百分比文本
ggplot(sum_slaughter_2021, aes(x = month, y = total_slaughter, fill = kind)) +
  geom_col() +
  # 添加顶部文本:指定text_data为数据源,y值用总高度
  geom_text(data = text_data, 
            aes(x = month, y = total_height, label = scales::percent(month_rate)),
            vjust = -0.3,  # 调整垂直位置,让文本在柱子上方
            size = 3.5) +
  labs(x = "月份", y = "屠宰总量", fill = "类别") +
  theme_minimal()

关键细节说明

  1. 解决美学长度不匹配:
    原错误是因为sum_slaughter_2021是每个月份对应多行(不同类别),而month_rate_2021是每个月份对应一行,直接引用会导致行数不匹配。通过按月份汇总总高度,再合并比率数据,得到每个月份一行的text_data,完美匹配x轴的12个分组。

  2. 文本位置调整:

    • vjust = -0.3:将文本向上偏移,避免被堆叠柱挡住;数值可根据实际柱子高度微调。
    • scales::percent():将小数格式的month_rate转换成百分比字符串(如0.25→25%),提升可读性。
  3. 数据匹配注意事项:
    确保两个数据集的month列类型完全一致(比如都是数值型1-12,或都是字符型"1月""2月"),否则left_join会匹配失败。

简化写法(无需单独预处理)

也可以直接在geom_text的data参数中完成数据汇总与合并,代码更紧凑:

ggplot(sum_slaughter_2021, aes(x = month, y = total_slaughter, fill = kind)) +
  geom_col() +
  geom_text(data = ~ .x %>% 
              group_by(month) %>% 
              summarise(total_height = sum(total_slaughter), .groups = "drop") %>%
              left_join(month_rate_2021, by = "month"),
            aes(x = month, y = total_height, label = scales::percent(month_rate)),
            vjust = -0.3, size = 3.5) +
  labs(x = "月份", y = "屠宰总量", fill = "类别") +
  theme_minimal()

内容的提问来源于stack exchange,提问作者seungwoolee

相关产品推荐
方舟 Agent Plan

超全模态模型 × Harness 升级,最新支持 Deepseek-V4.1-Flash、GLM-5.3 系列、Doubao-Seedream-5.0-pro、Kimi-K3 (部分), 限时 9.9 元起

最近更新时间:2026.07.31 17:01:12