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

如何在Matplotlib中放大正Y轴或压缩负Y轴以优化图表展示?

嘿,这个需求完全可以实现!Matplotlib里有好几种实用方法能帮你让正Y轴占据更多图表空间,同时压缩负半轴的展示区域,我给你整理了几个靠谱的方案:

方案1:手动调整Y轴范围与刻度(最快捷)

如果你的负半轴数据范围很小,直接手动设置Y轴的上下限,再自定义刻度分布就能快速达到效果。比如把负半轴的范围设得紧凑一点,正半轴保留足够的展示空间,同时让负半轴的刻度更稀疏,正半轴更密集。

import matplotlib.pyplot as plt
import numpy as np

# 模拟你的数据:3个负向数据,17个正向数据
x = np.arange(20)
y = np.concatenate([np.random.randn(3)*5, np.random.rand(17)*90 + 10])

plt.scatter(x, y)

# 手动设置Y轴范围:负半轴只留-15到0的空间,正半轴给到100
plt.ylim(-15, 100)

# 自定义刻度:负半轴只显示关键刻度,正半轴按间隔展示
plt.yticks([-10, 0, 20, 40, 60, 80, 100])

plt.title("压缩负半轴后的图表")
plt.show()
方案2:自定义非线性Y轴变换(灵活适配)

如果需要更灵活的比例调整(比如想让负半轴按比例压缩,正半轴保持原比例),可以自定义一个轴变换函数,让Matplotlib按照你设定的规则映射Y轴坐标。

import matplotlib.pyplot as plt
import numpy as np
from matplotlib.scale import FuncScale
from matplotlib.transforms import Transform

# 定义自定义变换:y<=0时压缩为原大小的20%,y>0时保持原比例
class CustomYTransform(Transform):
    input_dims = 1
    output_dims = 1
    is_separable = True

    def transform_non_affine(self, y):
        return np.where(y <= 0, y * 0.2, y)

    # 定义逆变换,确保图表交互时坐标正确
    def inverted(self):
        class InvertedCustomYTransform(Transform):
            def transform_non_affine(self, y):
                return np.where(y <= 0, y / 0.2, y)
        return InvertedCustomYTransform()

# 注册自定义刻度类型
FuncScale.register_scale('custom_y', CustomYTransform)

# 绘图
x = np.arange(20)
y = np.concatenate([np.random.randn(3)*5, np.random.rand(17)*90 + 10])

fig, ax = plt.subplots()
ax.scatter(x, y)

# 应用自定义Y轴变换
ax.set_yscale('custom_y')

# 手动设置刻度,确保负半轴标签正确显示
ax.set_yticks([-10, -5, 0, 20, 40, 60, 80, 100])
ax.set_yticklabels([-10, -5, 0, 20, 40, 60, 80, 100])

plt.title("自定义非线性Y轴变换")
plt.show()
方案3:拆分Y轴(直观区分正负区域)

如果想要最直观的展示效果,可以把Y轴拆成上下两部分:上半部分展示正半轴数据(占大部分空间),下半部分展示负半轴数据(占小部分空间),视觉上既保持整体感,又能突出正半轴的数据。

import matplotlib.pyplot as plt
import numpy as np

# 模拟数据
x = np.arange(20)
y = np.concatenate([np.random.randn(3)*5, np.random.rand(17)*90 + 10])

# 创建上下两个子轴,正半轴占8份空间,负半轴占1份
fig, (ax_pos, ax_neg) = plt.subplots(2, 1, sharex=True, 
                                     gridspec_kw={'height_ratios': [8, 1]})

# 正半轴绘图
ax_pos.scatter(x, y)
ax_pos.set_ylim(0, 100)
ax_pos.set_title("拆分Y轴:正半轴(上)+ 负半轴(下)")

# 负半轴绘图
ax_neg.scatter(x, y)
ax_neg.set_ylim(-15, 0)

# 隐藏中间的边框和刻度,让两个轴看起来像一个整体
ax_pos.spines['bottom'].set_visible(False)
ax_neg.spines['top'].set_visible(False)
ax_pos.tick_params(axis='x', which='both', bottom=False)
ax_neg.xaxis.tick_bottom()

# 添加连接斜线,提升视觉连贯性(可选)
d = .015  # 斜线的大小
kwargs = dict(transform=ax_pos.transAxes, color='k', clip_on=False)
ax_pos.plot((-d, +d), (-d, +d), **kwargs)
ax_pos.plot((1 - d, 1 + d), (-d, +d), **kwargs)

kwargs.update(transform=ax_neg.transAxes)
ax_neg.plot((-d, +d), (1 - d, 1 + d), **kwargs)
ax_neg.plot((1 - d, 1 + d), (1 - d, 1 + d), **kwargs)

plt.tight_layout()
plt.show()

这几个方案各有优势:第一种适合快速调整的简单场景;第二种能灵活适配各种压缩比例;第三种最直观,适合需要清晰区分正负数据的展示需求。你可以根据自己的实际数据和展示目标来选择~

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

相关产品推荐
方舟 Agent Plan

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

最近更新时间:2026.05.19 03:39:05