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

如何让叠加的散点图与matshow矩阵图尺寸同步缩放

实现散点标记与matshow格子尺寸同步适配的方法

问题原因

你目前使用的scatter函数的s参数为绝对面积单位(磅的平方),不会随矩阵维度变化、画布缩放自动匹配数据坐标下的格子尺寸,因此矩阵维度调整后会出现标记超出格子的问题。

推荐解决方案:使用数据坐标定义的Patch绘制标记

该方案无需反复调整参数,天生适配任意矩阵维度、任意缩放比例,标记尺寸始终和格子保持固定比例:

示例代码

import matplotlib.pyplot as plt
import numpy as np
from matplotlib.patches import RegularPolygon

# 5行20列的矩阵场景
ax = plt.axes()
mat = np.random.random((5, 20))
ax.matshow(mat, aspect='equal')

# 在坐标(1,2)处绘制向下的三角形,外接圆半径设为0.5即可刚好填满单个格子
# orientation参数设为np.pi对应三角形向下,和scatter的marker='v'效果完全一致
tri = RegularPolygon(
    xy=(1, 2),
    numVertices=3,
    radius=0.5,
    orientation=np.pi,
    facecolor="C0",
    edgecolor="none"
)
ax.add_patch(tri)

plt.show()

多标记场景

如果需要批量绘制多个标记,循环添加Patch即可:

# 示例:在多个位置绘制三角形
points = [(1,2), (3,4), (0,1)]
for x, y in points:
    tri = RegularPolygon(xy=(x,y), numVertices=3, radius=0.5, orientation=np.pi, facecolor="C0")
    ax.add_patch(tri)

备选方案:动态计算scatter的s参数

如果一定要使用scatter函数绘制,可以在matshow渲染完成后,基于当前轴的坐标变换动态计算s的取值:

import matplotlib.pyplot as plt
import numpy as np

def calc_adaptive_s(ax, fill_ratio=1.0):
    # 将数据坐标下1单位长度转换为显示像素长度
    p0 = ax.transData.transform((0, 0))
    p1 = ax.transData.transform((1, 0))
    pixel_per_unit = abs(p1[0] - p0[0])
    # 调整系数根据marker形状校准,v形marker校准为1350时刚好填满格子
    adjust_coef = 1350 * fill_ratio
    return (pixel_per_unit ** 2) * adjust_coef

# 调用示例
ax = plt.axes()
mat = np.random.random((5, 20))
ax.matshow(mat, aspect='equal')
# 必须在matshow绘制完成、轴范围确定后计算s
s = calc_adaptive_s(ax)
ax.scatter([1], [2], marker='v', s=s)
plt.show()

注意:该方案仅适用于绘制后不修改轴范围、不缩放的场景,如果后续手动调整画布需要重新计算s值。

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

相关产品推荐
方舟 Agent Plan

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

最近更新时间:2026.09.27 00:45:08