Python中比例堆叠条形图实现问题:现有代码如何优化堆叠效果?
实现比例堆叠条形图的代码修改方案
你当前的问题是多次调用sns.barplot时,每个条形都从y=0开始绘制,导致重叠。要实现堆叠效果,只需要给后续的条形指定bottom参数,让它基于前面类别的总和来绘制。以下是修改后的完整代码:
# 导入库 import pandas as pd import seaborn as sns import numpy as np import matplotlib.pyplot as plt import matplotlib.patches as mpatches # 读取数据 df = pd.read_csv('marsh fig 7.csv') plt.rcParams["axes.labelsize"] = 12 my_dpi = 96 # 补充缺失的my_dpi定义 plt.figure(figsize=(600/my_dpi, 300/my_dpi), dpi=my_dpi) # 计算每个类别的月度均值(sns.barplot默认绘制均值) monthly_means = df.groupby('Month').mean().reset_index() # 计算累积比例,作为堆叠的底部 monthly_means['C1_C2'] = monthly_means['Percent_C1'] + monthly_means['Percent_C2'] monthly_means['C1_C2_C3'] = monthly_means['C1_C2'] + monthly_means['Percent_C3'] monthly_means['C1_C2_C3_C4'] = monthly_means['C1_C2_C3'] + monthly_means['Percent_C4'] monthly_means['C1_C2_C3_C4_C5'] = monthly_means['C1_C2_C3_C4'] + monthly_means['Percent_C5'] # 绘制堆叠条形图 bar1 = sns.barplot(x="Month", y="Percent_C1", data=monthly_means, color='darkgreen') bar2 = sns.barplot(x="Month", y="Percent_C2", data=monthly_means, color='mediumseagreen', bottom=monthly_means['Percent_C1']) bar3 = sns.barplot(x="Month", y="Percent_C3", data=monthly_means, color='goldenrod', bottom=monthly_means['C1_C2']) bar4 = sns.barplot(x="Month", y="Percent_C4", data=monthly_means, color='sienna', bottom=monthly_means['C1_C2_C3']) bar5 = sns.barplot(x="Month", y="Percent_C5", data=monthly_means, color='steelblue', bottom=monthly_means['C1_C2_C3_C4']) # 注意:原代码中C6的y参数名称错误,这里修正为Percent_C6(请根据实际列名调整) bar6 = sns.barplot(x="Month", y="Percent_C6", data=monthly_means, color='darkblue', bottom=monthly_means['C1_C2_C3_C4_C5']) # 添加图例 bar1_patch = mpatches.Patch(color='darkgreen', label='% C1') bar2_patch = mpatches.Patch(color='mediumseagreen', label='% C2') bar3_patch = mpatches.Patch(color='goldenrod', label='% C3') bar4_patch = mpatches.Patch(color='sienna', label='% C4') bar5_patch = mpatches.Patch(color='steelblue', label='% C5') bar6_patch = mpatches.Patch(color='darkblue', label='% C6') # 调整y轴范围为0-100(因为是比例总和100%) plt.ylim(0, 100) plt.text(0, 97, "Marsh", ha='left', va='top', fontsize=12, fontweight='normal', color="black") # 双轴绘制水位线 ax2 = plt.twinx() df2 = pd.read_csv('SRS1 Water Level.csv') sns.pointplot(x="Month", y="Water Depth (cm)", data=df2, color="black", linestyles=':', label=None, errwidth=1, capsize=0.2, ax=ax2) plt.legend(handles=[bar1_patch, bar2_patch, bar3_patch, bar4_patch, bar5_patch, bar6_patch]) plt.show()
关键修改说明:
- 计算累积底部值:先按月份聚合计算各类别的均值,再依次计算前n个类别的总和,作为下一个条形的
bottom参数,确保每个条形堆叠在前一个之上。 - 修正C6的列名:原代码中C6的y参数写的是"Component Proportion",推测是笔误,需改为对应C6的列名(如
Percent_C6),请根据实际数据集调整。 - 调整y轴范围:原代码设置
ylim(0,40)不符合比例总和100%的需求,改为(0,100)。 - 补充缺失的
my_dpi定义:原代码中未定义my_dpi,这里补充了默认值96,可根据需求调整。
内容的提问来源于stack exchange,提问作者msmit275
相关产品推荐
相关产品推荐

