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

如何在Matplotlib堆叠条形图中正确使用mplcursors

问题解决:Matplotlib堆叠条形图与mplcursors的hover提示问题

问题根源分析

  • 统一显示最后一组数据的原因
    循环内的lambda函数会延迟绑定变量i,只有触发hover事件时才会读取i的当前值——循环结束后i已经指向最后一个索引(对应Tim),所以所有条形hover时都会显示Tim的数据。
  • 索引越界错误的原因
    加上sel.index后,触发事件时i同样指向最后一个索引(Tim),但Tim的提示文本列表仅含1个元素,而hover到其他用户的条形时,sel.index会是0、1、2这类大于0的数值,导致访问列表时超出范围。

修复后的完整代码

import matplotlib.pyplot as plt
import mplcursors

# 避免用dict作为变量名,防止覆盖Python内置类型
data_dict = {'Tom': ([10, 20, 40], [0, 15, 40], [1, 2, 3]),
             'John': ([10, 20], [0, 12], [5, 6]),
             'Tim': ([10], [0], [7])}
nameList = ['Tom', 'John', 'Tim']
y_pos = range(len(nameList))

for i in range(len(nameList)):
    name = nameList[i]
    heights = data_dict[name][0]
    bottoms = data_dict[name][1]
    texts = data_dict[name][2]
    # 生成堆叠条形
    bar_container = plt.bar(y_pos[i], height=heights, width=0.1, bottom=bottoms)
    # 用默认参数捕获当前迭代的texts,规避闭包延迟绑定问题
    cursor = mplcursors.cursor(bar_container, hover=True)
    cursor.connect("add", lambda sel, texts=texts: sel.annotation.set_text(texts[sel.index]))

plt.xticks(y_pos, nameList, rotation=90)
plt.show()

关键修改说明

  • 解决闭包延迟绑定:在lambda中添加texts=texts作为默认参数,让每一次循环迭代都捕获当前用户的提示文本列表,而非事件触发时才读取变量值。
  • 规范变量命名:将dict改为data_dict,避免与Python内置类型冲突。
  • 拆分变量提升可读性:把每个用户的高度、底部位置、提示文本拆分为单独变量,代码逻辑更清晰。

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

相关产品推荐
方舟 Agent Plan

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

最近更新时间:2026.07.26 23:58:16