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

如何在循环中设置Matplotlib堆叠条形图的bottom参数?

用For循环实现Matplotlib堆叠条形图并管理Bottom参数

核心思路

要解决这个问题,关键是先统一所有DataFrame的时间索引(缺失日期补0),再在循环中维护一个累加的bottom数组——初始为0,每次绘制完一组条形图后,将当前数据加到bottom上,确保下一组条形图叠在之前所有组的上方。


步骤1:统一时间索引

首先要把所有车辆的DataFrame对齐到同一时间轴上,确保每个日期都有对应数据(无数据的日期填0),这样循环时每组条形图的长度一致,bottom数组能正确匹配。

import pandas as pd
import matplotlib.pyplot as plt

# 模拟你的车辆数据(替换成实际的df_dangel、df_tepee等)
df_dangel = pd.DataFrame({'value': [10, 20]}, index=pd.to_datetime(['2024-01-01', '2024-01-03']))
df_tepee = pd.DataFrame({'value': [15, 5]}, index=pd.to_datetime(['2024-01-02', '2024-01-03']))

# 生成包含所有日期的完整时间索引
all_dates = pd.date_range(
    start=min(df_dangel.index.min(), df_tepee.index.min()),
    end=max(df_dangel.index.max(), df_tepee.index.max()),
    freq='D'  # 按天,可根据你的时间粒度调整
)

# 重新索引每个DataFrame,缺失日期填充0
df_dangel = df_dangel.reindex(all_dates, fill_value=0)
df_tepee = df_tepee.reindex(all_dates, fill_value=0)

# 将所有DataFrame和对应名称打包成列表,方便循环
vehicle_dfs = [("Dangel", df_dangel), ("Tepee", df_tepee)]

步骤2:循环绘制堆叠条形图

初始化bottom为全0数组,遍历每个DataFrame时,用当前bottom参数绘制条形图,之后更新bottom为当前值加上本次的条形高度,实现堆叠效果。

plt.figure(figsize=(10, 6))
# 初始bottom全为0,长度和日期数一致
bottom = [0] * len(all_dates)

for vehicle_name, df in vehicle_dfs:
    # 绘制当前车辆的条形图,指定bottom参数
    plt.bar(
        x=all_dates,
        height=df['value'],
        label=vehicle_name,
        bottom=bottom
    )
    # 更新bottom:累加当前数据,为下一组条形图做准备
    bottom = [current_bottom + value for current_bottom, value in zip(bottom, df['value'])]

# 美化图表
plt.xticks(rotation=45)
plt.legend(title="车辆类型")
plt.xlabel("日期")
plt.ylabel("数值")
plt.tight_layout()
plt.show()

关键注意事项

  • 如果你的DataFrame数值列名不同(比如有的是count,有的是amount),循环时统一取对应列即可,比如把df['value']替换成df['你的列名']。
  • 时间粒度可以根据需求调整pd.date_range的freq参数,比如按周('W')、按月('M')。
  • 若某日期所有车辆都无数据,对应的条形高度会是0,不会影响堆叠效果。

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

相关产品推荐
方舟 Agent Plan

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

最近更新时间:2026.08.20 11:42:23