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

Matplotlib/Seaborn绘图:将秒数坐标轴转为HH:MM:SS格式

解决Matplotlib/Seaborn中坐标轴显示HH:MM:SS时间格式的问题

你已经把时间转成秒数来绘图,这一步完全正确——因为箱线图需要数值型数据才能计算统计量。要让x轴显示HH:MM:SS格式,核心思路是保留数值型的秒数用于绘图,然后自定义坐标轴的刻度标签格式,而不是直接用datetime类型绘图(会带来时间轴的额外适配问题)。

这里给你两种实用的实现方法,都能完美解决你的需求:

方法一:自定义刻度格式化函数(最灵活推荐)

我们可以用matplotlib.ticker.FuncFormatter创建一个自定义函数,把秒数转换成HH:MM:SS格式的字符串,再应用到x轴上:

import pandas as pd
import matplotlib.pyplot as plt
import seaborn as sns
from matplotlib.ticker import FuncFormatter

# 模拟数据
df = pd.DataFrame({
    'sex': ['M', 'M', 'M', 'M', 'F', 'F', 'F', 'F'], 
    'race': ['5K', '5K', '10K', '10K', '5K', '5K', '10K', '10K'], 
    'time': ['00:20:16', '00:24:57', '00:49:17', '00:56:10', '00:26:31', '00:33:06', '00:58:29', '01:05:03']
})

# 转换时间为秒数(保留数值型用于绘图,用pandas内置方法更简洁)
df['time_sec'] = pd.to_timedelta(df['time']).dt.total_seconds()

# 定义格式化函数:秒数转HH:MM:SS格式
def format_time(sec, pos):
    hours = int(sec // 3600)
    minutes = int((sec % 3600) // 60)
    seconds = int(sec % 60)
    # 用02d补零,保证格式统一(比如0小时显示为00)
    return f"{hours:02d}:{minutes:02d}:{seconds:02d}"

# 绘图
order=['5K', '10K']
palette = ['#3498db', '#ff0080']
fig, ax = plt.subplots(figsize=(16, 8))
sns.boxplot(
    ax=ax, 
    data=df, 
    x='time_sec', 
    y='race', 
    hue='sex', 
    order=order, 
    palette=palette, 
    orient='h', 
    linewidth=2.5
)

# 把自定义格式应用到x轴
ax.xaxis.set_major_formatter(FuncFormatter(format_time))

# 调整图表文字提升可读性
plt.title('Race Results (HH:MM:SS)', fontsize=16)
plt.xlabel('Finish Time', fontsize=12)
plt.ylabel('Race Distance', fontsize=12)
plt.show()

关键细节说明:

  • 用pd.to_timedelta(df['time']).dt.total_seconds()替代了列表推导式,代码更简洁且不易出错
  • format_time函数自动处理秒数到时分秒的转换,02d格式确保小时/分钟/秒数不足两位时自动补零
  • FuncFormatter会自动把x轴上的每个秒数刻度值传入函数,替换成对应的时间字符串

方法二:利用Pandas Timedelta生成标签(适合简单场景)

如果你不想写自定义函数,也可以把秒数转回Timedelta类型,再提取字符串作为刻度标签:

# (前面数据处理、绘图部分和方法一一致)

# 获取x轴现有刻度,转换成Timedelta后提取时间字符串
ticks = ax.get_xticks()
tick_labels = [str(pd.to_timedelta(tick, unit='s')).split()[-1] for tick in ticks]
ax.set_xticklabels(tick_labels)

不过这种方法灵活性稍弱——默认的Timedelta字符串会带0 days前缀,需要用split()[-1]去掉,所以更推荐方法一。

这样修改后,你的x轴会清晰显示HH:MM:SS格式的时间,同时完全保留箱线图的统计计算逻辑,完美兼顾可读性和数据正确性。

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

相关产品推荐
方舟 Agent Plan

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

最近更新时间:2026.05.13 08:01:43