交互式 sns.heatmap 仅显示 x、y 悬停在颜色条上

问题描述 投票:0回答:1

示例脚本生成一个简单的图形。将鼠标悬停在数据上时,角落的坐标为 (x=, y=)。

No coordinates for the plot

悬停时颜色条会显示一些内容,但没有坐标的数据将被解释为 y。

Coordinates for the colorbar

import seaborn as sns
import numpy as np
import matplotlib.pyplot as plt

data = np.array([[15, 10], [20, 10]])

sns.heatmap(data, linewidth=0.01, square=True)
plt.show()

环境版本:

Ubuntu        22.04.2 LTS
python        3.11
matplotlib    3.7.1
numpy         1.24.3
seaborn       0.12.2

我试图挖掘seaborn生成的人物的轴的属性,但没有成功。在搜索解决此问题时,我没有找到其他 stackoverflow/其他论坛问题。

编辑: 当然,截取屏幕片段时光标是不可见的 -.-

python matplotlib seaborn heatmap interactive
1个回答
0
投票

这对于 Seaborn 本身来说不是问题,因为根本问题是 Matplotlib 的限制:如果您像 Seaborn 那样为轴设置标签,则该轴的鼠标悬停信息为空。

为了测试,让我们尝试相同的代码不带seaborn,带和不带标签:

import numpy as np
import matplotlib.pyplot as plt

data = np.array([[15, 10], [20, 10]])

def heatmap(title):
    plt.title(title)
    plt.colorbar(plt.imshow(data, cmap="inferno"))
    plt.xticks(np.arange(data.shape[0]))
    plt.yticks(np.arange(data.shape[0]))

heatmap("No Labels")
plt.show()

heatmap("Labels on X")
plt.gca().set_xticklabels("AB")
plt.show()

heatmap("Labels on X and Y")
plt.gca().set_xticklabels("AB")
plt.gca().set_yticklabels("CD")
plt.show()

No Labels Labels on X Labels on X and Y

(您可能已经注意到,在所有三种情况下,与seaborn相比,鼠标悬停时都有一个附加信息:(x,y)坐标处的数据值,在本例中为

[15.00]
。这是
imshow()
的礼貌,而(不幸的是)seaborn 使用类似的
pcolormesh()
缺少此额外信息)

一个可能的解决方案是覆盖用于显示此鼠标悬停信息的函数,因为据我所知,我们无法告诉seabornnot设置刻度标签。最简单的方法是覆盖

fmt_xdata()
/
fmt_ydata()
:

import seaborn as sns
import numpy as np
import matplotlib.pyplot as plt

data = np.array([[15, 10], [20, 10]])
ax = sns.heatmap(data, linewidth=0.01, square=True)

def fmt_data(v):
    return f"{v:.2f}"

ax.fmt_xdata = fmt_data
ax.fmt_ydata = fmt_data

plt.show()

overriding fmt_xdata/fmt_ydata

这已经恢复了设置标签时丢失的

pcolormesh
x=, y=
值。但是,如何改进这一点并像 imshow 一样显示
data
值呢?

为了完全控制鼠标悬停信息,我们覆盖

format_coord()
。将 matplotlib 文档中的 示例 简化为您的代码:

import seaborn as sns
import numpy as np
import matplotlib.pyplot as plt

data = np.array([[15, 10], [20, 10]])
ax = sns.heatmap(data, linewidth=0.01, square=True)

def format_coord(x, y):
    z = data[int(x), int(y)]
    return f"x={x:.2f}, y={y:.2f}\n[{z:.2f}]"

ax.format_coord = format_coord

plt.show()

overriding format_coord

© www.soinside.com 2019 - 2024. All rights reserved.