如何在R ggplot柱状图图例下方添加分组总计数标注
问题说明
使用如下数据集与ggplot2代码绘制性别分组的长度频率柱状图,需要在图例区域添加分组总计数标注,两个分组合计总样本量n=275。
示例数据集
structure(list(Geslacht = c("man", "man", "man", "man", "man", "man", "man", "vrouw", "vrouw", "vrouw", "vrouw", "vrouw", "vrouw", "vrouw", "vrouw"), Lengteklasse = c(6, 7, 8, 9, 10, 11, 12, 6, 7, 8, 9, 10, 11, 12, 13), Freq = c(1L, 9L, 19L, 21L, 35L, 22L, 5L, 2L, 13L, 19L, 37L, 45L, 40L, 6L, 1L)), class = c("grouped_df", "tbl_df", "tbl", "data.frame"), row.names = c(NA, -15L), groups = structure(list( Geslacht = c("man", "vrouw"), .rows = structure(list(1:7, 8:15), ptype = integer(0), class = c("vctrs_list_of", "vctrs_vctr", "list"))), class = c("tbl_df", "tbl", "data.frame" ), row.names = c(NA, -2L), .drop = TRUE))
初始绘图代码
ggplot(Freq_lengteklasse, aes(Lengteklasse, Freq, fill = Geslacht))+ geom_col()+ scale_x_continuous(breaks = seq(6,13, by = 1))+ scale_y_continuous(breaks = seq(0,80, by = 10))+ labs(x = "Lengteklasse (cm)", y = "Frequentie")+ scale_fill_manual(values=c('lightgray','black'))+ theme_classic()
实现方案
不需要依赖第三方扩展包,直接调整ggplot的标度和主题参数就能实现,操作如下:
- 提前计算需要标注的统计量
library(dplyr) # 计算分性别频数、总频数 n_man <- sum(Freq_lengteklasse$Freq[Freq_lengteklasse$Geslacht == "man"]) n_vrouw <- sum(Freq_lengteklasse$Freq[Freq_lengteklasse$Geslacht == "vrouw"]) total_n <- n_man + n_vrouw # 计算得总样本量为275
- 利用换行符
\n把标注内容嵌入图例的标题或标签中,配合主题参数调整行高避免文字重叠:
- 如果要把总n=275放在图例标题下方,直接修改
labs()里的fill标题即可:
ggplot(Freq_lengteklasse, aes(Lengteklasse, Freq, fill = Geslacht))+ geom_col()+ scale_x_continuous(breaks = seq(6,13, by = 1))+ scale_y_continuous(breaks = seq(0,80, by = 10))+ labs( x = "Lengteklasse (cm)", y = "Frequentie", fill = paste0("Geslacht\nn = ", total_n) )+ scale_fill_manual(values=c('lightgray','black'))+ theme_classic()+ theme(legend.title = element_text(lineheight = 1.2))
- 如果需要在每个分组名下方标注对应组的样本量,修改
scale_fill_manual()的labels参数即可:
ggplot(Freq_lengteklasse, aes(Lengteklasse, Freq, fill = Geslacht))+ geom_col()+ scale_x_continuous(breaks = seq(6,13, by = 1))+ scale_y_continuous(breaks = seq(0,80, by = 10))+ labs(x = "Lengteklasse (cm)", y = "Frequentie")+ scale_fill_manual( values=c('lightgray','black'), labels = c( paste0("man\nn = ", n_man), paste0("vrouw\nn = ", n_vrouw) ) )+ theme_classic()+ theme(legend.text = element_text(lineheight = 1.2))
- 如果需要把总样本量放在所有图例条目的最下方,只需要把总n的文本拼接在最后一个分组的标签后,多加一个换行符留出间距即可。
这种方式的标注位置会跟随图例自动调整,不会出现错位问题。
内容的提问来源于stack exchange,提问作者Pepijn95
相关产品推荐
相关产品推荐

