如何让多Axes对象Y轴匹配并使用NullFormatter隐藏其中一个Y轴?
问题:直方图与累积频率图Y轴匹配问题
我用subplot_mosaic布局创建了一个包含两个Axes对象的图表,左侧为直方图,右侧为累积频率图。

我希望两个Axes的刻度、网格和轴范围都与累积频率轴保持一致,但直方图的Y轴无法正常匹配。之后还需要隐藏累积频率Axes的刻度和刻度标签以减少界面杂乱,本示例中未使用NullFormatter()或设置刻度宽度为0,因为隐藏后会增加问题调试难度。
我已尝试在subplot_mosaic()中使用'sharey'参数、复制artists的方法(更倾向此类方案)以及多种手动设置方式,但效果有限。
当前图表是通过以下策略生成的:
ax1.set_ylim(ax2.get_ylim()) ax1.set_yticks(ax2.get_yticks()) ax1.set_yticklabels(ax2.get_yticklabels())
请问下一步该尝试什么方法?
完整代码示例:
import matplotlib as mpl import matplotlib.style from matplotlib.ticker import PercentFormatter, AutoMinorLocator, StrMethodFormatter, NullFormatter from matplotlib.figure import Figure from decimal import Decimal from PIL import Image with mpl.style.context(style=['dark_background', 'fast']): my_fig = Figure(**{'layout': 'constrained'}) my_fig.suptitle(**{'fontsize': 'x-large', 't': 'Histogram Cumulative Frequency Pair Plot'}) my_fig.supxlabel(**{'t': 'Bins'}) my_fig.supylabel(**{'t': 'Frequency '}) axes_dict = my_fig.subplot_mosaic(mosaic=[['histogram', 'cumulative_frequency']], gridspec_kw={'wspace': 0.0, 'hspace': 0.0}) axes_dict['histogram'].hist(**{'align': 'mid', 'alpha': 0.6, 'bins': [73.97720336914062, 73.98680114746094, 73.99639892578125, 74.00599670410156, 74.0156021118164, 74.02519989013672, 74.03479766845703], 'color': 'C0', 'histtype': 'bar', 'label': 'obs1', 'orientation': 'vertical', 'weights': [4, 7, 8, 5, 0, 1], 'x': [73.97720336914062, 73.98680114746094, 73.99639892578125, 74.00599670410156, 74.0156021118164, 74.02519989013672], 'zorder': 0.0}) axes_dict['histogram'].set_xticks( ticks=[73.97720336914062, 73.98680114746094, 73.99639892578125, 74.00599670410156, 74.0156021118164, 74.02519989013672, 74.03479766845703]) axes_dict['histogram'].set_xticklabels( labels=[73.97720336914062, 73.98680114746094, 73.99639892578125, 74.00599670410156, 74.0156021118164, 74.02519989013672, 74.03479766845703]) axes_dict['histogram'].spines['top'].set_visible(False) axes_dict['histogram'].spines['left'].set_visible(False) axes_dict['histogram'].spines['right'].set_visible(False) axes_dict['histogram'].yaxis.set_minor_locator(AutoMinorLocator()) axes_dict['histogram'].tick_params(**{'labelrotation': 90.0, 'which': 'major', 'axis': 'x'}) axes_dict['histogram'].tick_params(**{'grid_linestyle': 'dashed', 'which': 'major', 'axis': 'y'}) axes_dict['histogram'].tick_params(**{'grid_alpha': 0.2, 'which': 'minor', 'axis': 'y'}) axes_dict['histogram'].xaxis.set_major_formatter(StrMethodFormatter('{x:.3f}')) axes_dict['cumulative_frequency'].hist(**{'align': 'mid', 'alpha': 0.6, 'bins': [73.97720336914062, 73.98680114746094, 73.99639892578125, 74.00599670410156, 74.0156021118164, 74.02519989013672, 74.03479766845703], 'color': 'C0', 'histtype': 'bar', 'label': 'obs1', 'orientation': 'vertical', 'weights': [Decimal('4'), Decimal('11'), Decimal('19'), Decimal('24'), Decimal('24'), Decimal('25')], 'x': [73.97720336914062, 73.98680114746094, 73.99639892578125, 74.00599670410156, 74.0156021118164, 74.02519989013672], 'zorder': 0.0}) axes_dict['cumulative_frequency'].set_xticks( ticks=[73.97720336914062, 73.98680114746094, 73.99639892578125, 74.00599670410156, 74.0156021118164, 74.02519989013672, 74.03479766845703]) axes_dict['cumulative_frequency'].set_xticklabels( labels=[73.97720336914062, 73.98680114746094, 73.99639892578125, 74.00599670410156, 74.0156021118164, 74.02519989013672, 74.03479766845703]) axes_dict['cumulative_frequency'].spines['top'].set_visible(False) axes_dict['cumulative_frequency'].spines['left'].set_visible(False) axes_dict['cumulative_frequency'].spines['right'].set_visible(False) axes_dict['cumulative_frequency'].yaxis.set_minor_locator(AutoMinorLocator()) axes_dict['cumulative_frequency'].tick_params(**{'labelrotation': 90.0, 'which': 'major', 'axis': 'x'}) axes_dict['cumulative_frequency'].tick_params(**{'grid_linestyle': 'dashed', 'which': 'major', 'axis': 'y'}) axes_dict['cumulative_frequency'].tick_params(**{'grid_alpha': 0.2, 'which': 'minor', 'axis': 'y'}) axes_dict['cumulative_frequency'].xaxis.set_major_formatter(StrMethodFormatter('{x:.3f}')) axes_dict['histogram'].set_ylim(axes_dict['cumulative_frequency'].get_ylim()) axes_dict['histogram'].set_yticks(axes_dict['cumulative_frequency'].get_yticks()) axes_dict['histogram'].set_yticklabels(axes_dict['cumulative_frequency'].get_yticklabels()) axes_dict['histogram'].set_yticks(ticks=axes_dict['histogram'].get_yticks()) axes_dict['histogram'].set_yticklabels(labels=['', '5', '10', '15', '20', '25', '30']) my_fig.savefig('example_figure_for_stackoverflow.png') Image.open('example_figure_for_stackoverflow.png').show()
解决方案
核心问题分析
你当前手动设置Y轴后又覆盖了刻度标签,且sharey参数未生效可能是因为绘制直方图后才设置,或参数传递方式错误;另外累积频率图使用Decimal类型权重,可能导致轴刻度计算出现差异。
具体修复步骤
- 正确使用
sharey参数:创建subplot_mosaic时指定sharey='all',让两个Axes共享Y轴,累积频率图的Y轴设置会自动同步到直方图。 - 统一权重数据类型:将累积频率图的权重从
Decimal改为普通整数,避免类型不一致导致的刻度异常。 - 移除重复手动刻度设置:删除后续覆盖Y轴刻度的代码,避免冲突。
- 隐藏累积频率轴刻度:调试完成后,用
tick_params隐藏右侧轴的刻度和标签。
修改后的完整代码
import matplotlib as mpl import matplotlib.style from matplotlib.ticker import PercentFormatter, AutoMinorLocator, StrMethodFormatter, NullFormatter from matplotlib.figure import Figure from PIL import Image with mpl.style.context(style=['dark_background', 'fast']): my_fig = Figure(**{'layout': 'constrained'}) my_fig.suptitle(**{'fontsize': 'x-large', 't': 'Histogram Cumulative Frequency Pair Plot'}) my_fig.supxlabel(**{'t': 'Bins'}) my_fig.supylabel(**{'t': 'Frequency '}) # 指定sharey='all'实现Y轴共享 axes_dict = my_fig.subplot_mosaic(mosaic=[['histogram', 'cumulative_frequency']], gridspec_kw={'wspace': 0.0, 'hspace': 0.0}, sharey='all') # 直方图设置 axes_dict['histogram'].hist(**{'align': 'mid', 'alpha': 0.6, 'bins': [73.97720336914062, 73.98680114746094, 73.99639892578125, 74.00599670410156, 74.0156021118164, 74.02519989013672, 74.03479766845703], 'color': 'C0', 'histtype': 'bar', 'label': 'obs1', 'orientation': 'vertical', 'weights': [4, 7, 8, 5, 0, 1], 'x': [73.97720336914062, 73.98680114746094, 73.99639892578125, 74.00599670410156, 74.0156021118164, 74.02519989013672], 'zorder': 0.0}) axes_dict['histogram'].set_xticks( ticks=[73.97720336914062, 73.98680114746094, 73.99639892578125, 74.00599670410156, 74.0156021118164, 74.02519989013672, 74.03479766845703]) axes_dict['histogram'].xaxis.set_major_formatter(StrMethodFormatter('{x:.3f}')) axes_dict['histogram'].spines['top'].set_visible(False) axes_dict['histogram'].spines['right'].set_visible(False) axes_dict['histogram'].yaxis.set_minor_locator(AutoMinorLocator()) axes_dict['histogram'].tick_params(**{'labelrotation': 90.0, 'which': 'major', 'axis': 'x'}) axes_dict['histogram'].tick_params(**{'grid_linestyle': 'dashed', 'which': 'major', 'axis': 'y'}) axes_dict['histogram'].tick_params(**{'grid_alpha': 0.2, 'which': 'minor', 'axis': 'y'}) # 累积频率图设置,权重改为普通整数 axes_dict['cumulative_frequency'].hist(**{'align': 'mid', 'alpha': 0.6, 'bins': [73.97720336914062, 73.98680114746094, 73.99639892578125, 74.00599670410156, 74.0156021118164, 74.02519989013672, 74.03479766845703], 'color': 'C0', 'histtype': 'bar', 'label': 'obs1', 'orientation': 'vertical', 'weights': [4, 11, 19, 24, 24, 25], 'x': [73.97720336914062, 73.98680114746094, 73.99639892578125, 74.00599670410156, 74.0156021118164, 74.02519989013672], 'zorder': 0.0}) axes_dict['cumulative_frequency'].set_xticks( ticks=[73.97720336914062, 73.98680114746094, 73.99639892578125, 74.00599670410156, 74.0156021118164, 74.02519989013672, 74.03479766845
相关产品推荐
相关产品推荐

