Seaborn 热图更改 yticks 的日期频率

Posted

技术标签:

【中文标题】Seaborn 热图更改 yticks 的日期频率【英文标题】:Seaborn heatmap change date frequency of yticks 【发布时间】:2022-01-05 22:51:09 【问题描述】:

我的问题和这个话题遇到的类似:Change heatmap's yticks for multi-index dataframe

我希望每 6 个月有一次 yticks,它们是我的数据框的索引。但我无法让它工作。

问题是我的数据框是 13500*290 并且链接中给出的答案需要很长时间并且不起作用(见下图)。

这是我的代码示例,没有链接中的解决方案,这部分对我来说很好:

import pandas as pd
import numpy as np
import matplotlib.pyplot as plt
import seaborn as sns
from datetime import datetime

df = pd.DataFrame(index = pd.date_range(datetime(1984, 6, 10), datetime(2021, 1, 14), freq='1D') )

for i in range(0,290):
    df['Pt0'.format(i)] = np.random.random(size=len(df))
    
f, ax = plt.subplots(figsize=(20,20))
sns.heatmap(df, cmap='PuOr', vmin = np.min(np.min(df)), vmax = np.max(np.max(df)), cbar_kws="label": "Ice Velocity (m/yr)") 

这部分对我不起作用,并产生下图,它不应该在 yaxis 上有一堆 ylabels:

f, ax = plt.subplots(figsize=(20,20))
years = df.index.get_level_values(0)
ytickvalues = [year if index in (2, 7, 12) else '' for index, year in enumerate(years)]
sns.heatmap(df, cmap='PuOr', vmin = np.min(np.min(df)), vmax = np.max(np.max(df)), cbar_kws="label": "Ice Velocity (m/yr)", yticklabels = ytickvalues) 

【问题讨论】:

由于 DataFrame 的大小,我认为无论 ytickvalues 如何渲染热图都需要很长时间。在创建热图时,也许您可​​以将数据缩减为每 6 个月一次? 我真的不想进行下采样,因为我对显示的所有变体都感兴趣,而且使用 6 个月的下采样确实会使情节难以解释。但是漫长的等待时间并不是问题,主要问题是它根本不起作用 在我的系统上,这可以正常工作,并且可以正确缩放 ylabels 的数量,并以 1.47 s ± 17.6 ms 每个循环(平均值 ± 标准开发 7 次运行,1 个循环每个)。确保您在 seaborn (0.11.2) 和 matplotlib (3.4.3) 上使用当前版本。见code and plot 如果你使用 conda,那么在 Anaconda 提示符处conda update --all 13_000 天没有平均,在普通尺寸的显示器上查看时几乎肯定会出现混叠。如果您的标志中有任何高频信息,您应该先平滑然后再向下采样。 【参考方案1】:

这里有几种方法可以根据您的用例调整该链接(每 6 个月 1 个标签):

    任一: 显示一个空字符串,但在 1 月 1 日和 7 月 1 日除外(即,当 %m%d 评估为 01010701 时)

    labels = [date if date.strftime('%m%d') in ['0101', '0701'] else ''
              for date in df.index.date]
    

    或者:显示一个空字符串,除了每 ~365/2 天(即row % 183 == 0

    labels = [date if row % 183 == 0 else ''
              for row, date in enumerate(df.index.date)]
    

请注意,您没有 MultiIndex,因此您可以使用 df.index.date(不需要 get_level_values)。


这是您的df 的最小化版本的输出:

sns.heatmap(df, cmap='PuOr', cbar_kws='label': 'Ice Velocity (m/yr)',
            vmin=df.values.min(), vmax=df.values.max(),
            yticklabels=labels)

【讨论】:

似乎 seaborn 0.11.2 和 matplotlib 3.4.3 已经将标签间距设置为可接受的密度。这个答案允许指定标签之间的精确时间距离。 @TrentonMcKinney 是的,对于默认间距,我得到与您的输出类似的东西(尽管我的系统 比 1.47 秒长)

以上是关于Seaborn 热图更改 yticks 的日期频率的主要内容,如果未能解决你的问题,请参考以下文章

更改 Seaborn 热图中刻度标签的旋转

带有日期时间轴的 Seaborn 热图

热图中的日期轴 seaborn

更改seaborn热图的轴标签[重复]

更改 seaborn 热图颜色条上的刻度大小

更改 seaborn 热图中的某些方块