如何以某变量为X轴绘制另一变量取值占比的柱状图?
问题根因与解决办法
你遇到的三个问题核心是直接使用原始行级数据绘图,没有提前做分组汇总,同时函数参数映射不匹配:
问题1:Y轴显示计数而非占比
你使用stat='identity'时,ggplot会直接对每个肤色组的Elected字段求和,得到的是当选人数而非占比,需要先按肤色分组计算每组的当选比例:
library(dplyr) library(ggplot2) # 预处理:保留1-11所有肤色刻度,计算每个肤色的当选占比 summary_data <- data %>% # 补全1-11所有肤色值,无数据的组默认Elected为0 tidyr::complete(SkinTone = 1:11, fill = list(Elected = 0)) %>% group_by(SkinTone) %>% # 平均值即当选占比(Elected为0/1哑变量) summarise(elect_pct = mean(Elected), .groups = "drop")
问题2:出现黑色块
你设置了col="black"给条形加黑色边框,同时用原始行级数据绘图时,每个观测值会作为单独的小条形堆叠,大量小边框挤压重叠就形成了黑色块,使用汇总后的数据绘图,每个肤色仅对应1个条形,即可解决该问题。
问题3:geom_density报错
geom_density()是用来绘制单变量的分布密度,默认仅需要X轴映射,不需要传入Y轴参数。如果你需要展示当选比例的变化趋势,使用适配双变量映射的geom_smooth()即可,不会出现映射报错。
完整可运行代码
ggplot(data = summary_data, mapping = aes(x = SkinTone, y = elect_pct)) + geom_bar(stat='identity', fill="yellow", col="black", width=1, alpha=.2) + # 可选:添加平滑趋势线 geom_smooth(se = FALSE, color = "darkred", linewidth = 1) + coord_cartesian(xlim = c(0.5,11.5)) + scale_x_continuous(breaks = 1:11, expand = expansion(add = .5)) + # Y轴格式化为百分比更符合需求 scale_y_continuous(labels = scales::percent, limits = c(0,1)) + labs(title="Skin Tone Electoral Success Barplot", x="Skin Tone", y="Percentage of Candidates Elected")
注意:你原代码中X轴映射的
Tone与数据集列名SkinTone不一致,需修正为实际列名避免报错。
内容的提问来源于stack exchange,提问作者falling balloons
相关产品推荐
相关产品推荐

