如何在Altair散点图中为单个数据点设置独特形状?
Altair散点图自定义特定数据点形状解决方案
需求与数据集
需求:使用Altair绘制散点图时,仅股票代码为“V”的数据点采用独特形状(如菱形),其余所有股票数据点统一使用圆形。
现有数据集如下:
import pandas as pd ratio_df = pd.DataFrame(data={ "symbol": { "0": "V", "1": "MA", "2": "FI" }, "shortName": { "0": "Visa Inc.", "1": "Mastercard Incorporated", "2": "Fiserv, Inc." }, "value": { "0": 31.446135, "1": 38.91105, "2": 30.7025 } })
最初错误尝试
最初编写的代码无法实现需求,代码如下:
import altair as alt chart = ( alt.Chart(ratio_df) .mark_point() .encode( row=alt.Row("metric:N"), x=alt.X("value:Q"), y=alt.Y("symbol:N"), tooltip=alt.Tooltip(["shortName:N", "metric:N", "value:Q"]), color=alt.Color("shortName:N"), shape=alt.condition("datum.symbol == V", "diamond", "circle"), ) )
尝试过的无效方案
先后尝试多种方案均未达到预期效果:
- 方案1:
encode(..., shape=alt.condition("datum.symbol == V", alt.value("diamond"), alt.value("circle"))):报错提示此处无法使用alt.condition - 方案2:
encode(..., shape=alt.Shape("symbol:N")):每个股票代码对应不同形状,不符合统一其余点形状的需求 - 方案3:
mark_point(..., shape=alt.Shape("symbol:N")):同样每个股票代码对应不同形状,不符合需求 - 方案4:
mark_point(..., shape=alt.condition("datum.symbol == V", alt.value("diamond"), alt.value("circle"))):报错提示shape需为字符串类型 - 方案5:分组适配方案:仅支持两类分组场景,无法适配多股票数据的情况
可行解决方案
通过构建形状映射列表,结合alt.Scale的range参数实现需求,具体代码如下:
import altair as alt base_symbol: str = "V" marker_shape: list[str] = [] # 为每个唯一股票代码匹配对应形状 for distinct_symbol in ratio_df["symbol"].drop_duplicates().sort_values(): if distinct_symbol == base_symbol: marker_shape.append("diamond") # 为目标股票设置独特形状 else: marker_shape.append("circle") # 其余股票统一用圆形 chart = ( alt.Chart(ratio_df) .mark_point() .encode( row=alt.Row("metric:N"), x=alt.X("value:Q"), y=alt.Y("symbol:N"), tooltip=alt.Tooltip(["shortName:N", "metric:N", "value:Q"]), color=alt.Color("shortName:N"), # 通过scale的range绑定自定义形状列表 shape=alt.Shape("shortName", scale=alt.Scale(range=marker_shape)), ) ) chart
内容的提问来源于stack exchange,提问作者engineer-x
相关产品推荐
相关产品推荐

