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

如何用Seaborn为DataFrame中每个唯一name生成多hue折线图?

解决Seaborn折线图按name分图、hue区分多列分数的问题

首先看你的原始数据结构:

name,id,score1,score2,score3
ax,1,32,43,32
sy,1,34,22,22
ax,2,22,6,8
ax,3,10,5,4
bz,1,22,2,2
sy,2,10,1,0
bz,2,9,8,1

你需要的效果是每个name对应一个子图,x轴为id,y轴为分数值,用hue区分三个分数列。核心问题是Seaborn的hue需要对应数据中的一列分类值,但你的分数分散在多列,所以第一步要把宽表转成适合Seaborn的长表格式。

具体步骤

  1. 数据格式转换:用pandas.melt()把多个分数列合并成两列——一列标记分数类型(score1/score2/score3),一列存储对应分数值。
  2. 分面绘图:用seaborn.FacetGrid按name拆分子图,再在每个子图里绘制折线图,指定x、y和hue对应转换后的列。

完整代码

import pandas as pd
import seaborn as sns
import matplotlib.pyplot as plt

# 读取数据(如果是从csv文件读取,替换为pd.read_csv('your_file.csv'))
data = pd.DataFrame({
    'name': ['ax', 'sy', 'ax', 'ax', 'bz', 'sy', 'bz'],
    'id': [1, 1, 2, 3, 1, 2, 2],
    'score1': [32, 34, 22, 10, 22, 10, 9],
    'score2': [43, 22, 6, 5, 2, 1, 8],
    'score3': [32, 22, 8, 4, 2, 0, 1]
})

# 宽表转长表:保留name和id作为标识列,合并score1/2/3为长格式
melted_data = pd.melt(
    data,
    id_vars=['name', 'id'],       # 不需要转换的列
    value_vars=['score1', 'score2', 'score3'],  # 要合并的分数列
    var_name='score_type',        # 新的分类列名(标记分数类型)
    value_name='score_value'      # 新的数值列名(存储分数值)
)

# 创建分面网格,按name拆分子图,共享x/y轴刻度
g = sns.FacetGrid(melted_data, col='name', sharex=True, sharey=True)

# 在每个子图绘制折线图,指定x、y、hue对应列
g.map(sns.lineplot, 'id', 'score_value', 'score_type', marker='o')

# 添加图例(FacetGrid默认不自动生成,手动补充)
g.add_legend(title='Score Type')

# 调整布局避免标签重叠
plt.tight_layout()
plt.show()

代码说明

  • pd.melt()是核心操作:将原本每行对应一组name+id+三个分数的宽表,转成每行对应一组name+id+一个分数类型+对应值的长表,让Seaborn的hue能通过score_type列区分不同线条。
  • FacetGrid(col='name')会自动为每个唯一的name生成独立子图,sharex/sharey参数保证子图轴刻度一致,便于对比不同name的分数变化。
  • map()方法将lineplot应用到每个子图,参数依次对应x、y、hue的列名。

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

相关产品推荐
方舟 Agent Plan

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

最近更新时间:2026.07.31 19:20:53