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

Plotly scattermapbox子图图例颜色匹配问题求助

问题原因分析

你的代码存在两个核心问题导致图例颜色显示异常:

  1. 颜色与类别对应关系混乱:用set(Color)和set(Category)构建cats字典时,集合是无序结构,破坏了最初为每个Category分配颜色的对应关系。
  2. Trace的颜色与数据范围错误:循环添加Trace时,误用了整个df_type_1/df_type_2的坐标和颜色列,而非当前类别筛选后的子集;同时marker颜色传入多值数组,导致图例无法正确识别单一类别对应的颜色。
修正后的代码
import pandas as pd
import numpy as np
import plotly.graph_objects as go
from plotly.subplots import make_subplots
import plotly.express as px

df = pd.DataFrame({'Type' : ['1','1','1','1','1','2','2','2','2','2'],
                   'Category' : ['A','B','C','D','E','A','B','C','D','E']
                  })

# 为每个Category分配唯一颜色,保留对应关系
color_map = dict(zip(df['Category'].unique(), px.colors.qualitative.Alphabet[:len(df['Category'].unique())]))
df['Color'] = df['Category'].map(color_map)

df = pd.concat([df]*10, ignore_index = True)
df['Lat'] = np.random.randint(0, 20, 100)
df['Lon'] = np.random.randint(0, 20, 100)

# 构建正确的颜色-类别映射(从已有的对应关系中提取)
cats = {v: k for k, v in color_map.items()}

df_type_1 = df[df['Type'] == '1'].copy()
df_type_2 = df[df['Type'] == '2'].copy()

fig = make_subplots(
    rows = 1, 
    cols = 2,
    specs = [[{"type": "scattermapbox"}, {"type": "scattermapbox"}]],
    vertical_spacing = 0.05,
    horizontal_spacing = 0.05
)

# 第一个子图:按类别添加Trace
for c in df_type_1['Color'].unique():
    df_color = df_type_1[df_type_1['Color'] == c]
    fig.add_trace(go.Scattermapbox(
                        lat = df_color['Lat'],  # 使用筛选后的子集坐标
                        lon = df_color['Lon'],
                        mode = 'markers',
                        name = cats[c],  # 使用正确的类别名称
                        marker = dict(color = c),  # 设置单一颜色,而非数组
                        opacity = 0.5,
                        showlegend=True  # 第一个子图显示图例
                        ),
              row = 1,
              col = 1
             )

# 第二个子图:按类别添加Trace,关闭图例避免重复
for c in df_type_2['Color'].unique():
    df_color = df_type_2[df_type_2['Color'] == c]
    fig.add_trace(go.Scattermapbox(
                        lat = df_color['Lat'],
                        lon = df_color['Lon'],
                        mode = 'markers',
                        name = cats[c],
                        marker = dict(color = c),
                        opacity = 0.5,
                        showlegend=False  # 第二个子图不显示图例,避免重复
                        ),
              row = 1,
              col = 2
             )    

fig.update_layout(height = 600, width = 800, margin = dict(l = 10, r = 10, t = 30, b = 10));

fig.update_layout(mapbox1 = dict(zoom = 2, style = 'carto-positron'),
                  mapbox2 = dict(zoom = 2, style = 'carto-positron'),
                  )

fig.show()
关键修改说明
  • 修复颜色-类别映射:直接基于最初分配的color_map构建反向字典,保证颜色和类别对应关系完全一致,避免集合无序带来的混乱。
  • 使用筛选后的数据集:循环中只使用当前颜色对应的子集数据,确保每个Trace仅包含对应类别的点。
  • 设置单一marker颜色:将marker.color设为当前循环的颜色值c,而非整个颜色列,这样图例中每个条目都会显示对应类别的正确颜色。
  • 控制图例显示:关闭第二个子图的图例,避免同一类别在图例中重复出现,保持图例简洁。

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

相关产品推荐
方舟 Agent Plan

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

最近更新时间:2026.08.18 06:35:30