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

如何基于给定DataFrame为Plotly桑基图准备数据?

用Pandas数据绘制Plotly桑基图的数据准备方法

1. 明确桑基图数据要求

Plotly桑基图依赖两类核心数据:

  • 节点(nodes):所有出现在层级中的唯一标识,每个节点对应一个专属索引。
  • 链接(links):节点间的关联关系,包含源节点索引、目标节点索引,以及代表流量的数值。

你的需求是构建Id → ColA → ColB → ColC的层级关系,以下是具体实现步骤:

2. 导入依赖库

import pandas as pd
import plotly.graph_objects as go

3. 定义原始数据

df = pd.DataFrame({'Id': [1, 2, 3, 4], 'ColA': [30, 20, 20,30], 'ColB':[50, 20, 30,70], 
'ColC':[70, 30, 20,80]})

4. 准备节点数据

收集所有层级的唯一节点,并创建节点与索引的映射:

# 收集所有节点(Id + 各列数值),转字符串避免数值类型冲突
nodes = []
nodes.extend(df['Id'].astype(str).tolist())
for col in ['ColA', 'ColB', 'ColC']:
    nodes.extend(df[col].astype(str).tolist())

# 去重并保留首次出现顺序
nodes = list(dict.fromkeys(nodes))

# 创建节点到索引的映射字典
node_map = {node: idx for idx, node in enumerate(nodes)}

5. 准备链接数据

提供两种方式,可根据需求选择:

方式1:保留每条原始路径(流量为1)

遍历每一行数据,依次建立相邻列的链接:

links = {'source': [], 'target': [], 'value': []}

for _, row in df.iterrows():
    # Id → ColA
    links['source'].append(node_map[str(row['Id'])])
    links['target'].append(node_map[str(row['ColA'])])
    links['value'].append(1)
    
    # ColA → ColB
    links['source'].append(node_map[str(row['ColA'])])
    links['target'].append(node_map[str(row['ColB'])])
    links['value'].append(1)
    
    # ColB → ColC
    links['source'].append(node_map[str(row['ColB'])])
    links['target'].append(node_map[str(row['ColC'])])
    links['value'].append(1)

方式2:聚合相同路径的流量(流量为出现次数)

如果需要体现相同节点对的出现频次,用分组统计生成链接:

links = {'source': [], 'target': [], 'value': []}

# 统计Id到ColA的流量
for _, row in df.groupby(['Id', 'ColA']).size().reset_index(name='count').iterrows():
    links['source'].append(node_map[str(row['Id'])])
    links['target'].append(node_map[str(row['ColA'])])
    links['value'].append(row['count'])

# 统计ColA到ColB的流量
for _, row in df.groupby(['ColA', 'ColB']).size().reset_index(name='count').iterrows():
    links['source'].append(node_map[str(row['ColA'])])
    links['target'].append(node_map[str(row['ColB'])])
    links['value'].append(row['count'])

# 统计ColB到ColC的流量
for _, row in df.groupby(['ColB', 'ColC']).size().reset_index(name='count').iterrows():
    links['source'].append(node_map[str(row['ColB'])])
    links['target'].append(node_map[str(row['ColC'])])
    links['value'].append(row['count'])

6. 绘制桑基图

fig = go.Figure(data=[go.Sankey(
    node = dict(
        pad = 15,
        thickness = 20,
        line = dict(color = "black", width = 0.5),
        label = nodes  # 节点显示标签
    ),
    link = dict(
        source = links['source'],
        target = links['target'],
        value = links['value']
    )
)])

fig.update_layout(title_text="Id到各列数值的桑基图", font_size=10)
fig.show()

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

相关产品推荐
方舟 Agent Plan

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

最近更新时间:2026.07.31 06:06:45