如何在ggplot2中叠加两个人口金字塔图并显示对应图例
叠加双人口金字塔图的ggplot2实现方案
需求说明
需要在ggplot2中绘制叠加式人口金字塔:以普查(census)数据生成浅色半透明底图,再叠加调查(survey)数据的深色金字塔(darkred对应女性、steelblue对应男性),同时图例需正确显示Male (c/s)、Female (c/s)标签(c代表普查,s代表调查)。
实现步骤
- 基于普查数据绘制基础柱状图,设置半透明浅色填充
- 在基础图上叠加调查数据的柱状图层,使用指定深色填充
- 通过
scale_fill_manual统一配置四类性别标签对应的颜色,确保图例正确映射 - 修正原代码中的语法错误,调整文本标签、坐标轴及主题样式
完整代码
library(tidyverse) library(ggplot2) # 数据准备 census <- data.frame( age = c("20-29", "30-39", "40-49", "50-59", "60-69", "70+"), PopPerc = c(12.45, 14.14, 16.56, 14.73, 13.77, 11.00, -11.18, -13.13, -16.67, -15.10, -14.60, -13.82), sex = c("Male (c)", "Male (c)", "Male (c)", "Male (c)", "Male (c)", "Male (c)", "Female (c)", "Female (c)", "Female (c)", "Female (c)", "Female (c)", "Female (c)"), signal = c(1, 1, 1, 1, 1, 1, -1, -1, -1, -1, -1, -1) ) survey <- data.frame( age = c("20-29", "30-39", "40-49", "50-59", "60-69", "70+"), PopPerc = c(12.18, 24.70, 27.54, 19.22, 11.77, 4.60, -11.94, -25.76, -29.59, -18.11, -10.84, -3.76), sex = c("Male (s)", "Male (s)", "Male (s)", "Male (s)", "Male (s)", "Male (s)", "Female (s)", "Female (s)", "Female (s)", "Female (s)", "Female (s)", "Female (s)"), signal = c(1, 1, 1, 1, 1, 1, -1, -1, -1, -1, -1, -1) ) # 构建叠加金字塔图 pyramid_plot <- census %>% ggplot(aes(x = age, y = PopPerc)) + # 普查数据底层:半透明浅色 geom_bar(aes(fill = sex), stat = 'identity', alpha = 0.5) + # 普查数据百分比标签 geom_text(aes(y = PopPerc + signal * 0.3, label = abs(PopPerc))) + # 调查数据上层:深色,调整宽度避免完全遮挡底层 geom_bar(data = survey, aes(fill = sex), stat = 'identity', width = 0.7) + # 翻转坐标轴形成金字塔形态 coord_flip() + # 统一配置填充颜色,对应所有四类标签 scale_fill_manual( name = '', values = c( "Female (c)" = alpha("lightpink", 0.5), "Male (c)" = alpha("lightblue1", 0.5), "Female (s)" = "darkred", "Male (s)" = "steelblue" ) ) + # Y轴格式化为百分比显示 scale_y_continuous( labels = function(x) paste(abs(x), '%') ) + # 图表标签设置 labs( x = '', y = '参与者占比', title = '普查与调查人口金字塔叠加图' ) + # 主题样式调整 theme_classic() + theme( axis.text.x = element_text(vjust = 0.5), panel.grid.major.y = element_line(color = 'lightgray', linetype = 'dashed'), legend.position = 'top', legend.justification = 'center' ) # 输出图形 pyramid_plot
代码说明
- 两次调用
geom_bar实现图层叠加,普查数据作为底层,调查数据通过width参数调整宽度,避免完全遮挡底层 scale_fill_manual明确指定四个sex类别对应的颜色,确保图例与图形颜色一一对应- 保留原有的文本标签、坐标轴翻转逻辑,同时修正了原代码中的语法错误
内容的提问来源于stack exchange,提问作者Chris T.
相关产品推荐
相关产品推荐

