Python多子图绘制因整除余值导致索引越界的优雅解决方案
嘿,这个问题我之前做批量可视化时也碰到过!用12×12布局展示70个子图,直接硬循环要么索引越界,要么堆一堆if-else显得代码乱糟糟的。这里有两个优雅高效的解决方案,完美适配你的需求:
方案一:严格12×12布局,批量隐藏空轴
这种方式完全符合你想要快速查看的12×12布局,先创建所有子图,只绘制前70个,剩余的空轴直接批量隐藏,逻辑清晰且代码简洁:
import matplotlib.pyplot as plt import pandas as pd # 假设你的变量已经加载完成:warDf、meanDf、time、pcmean、ncmean fig, axes = plt.subplots(12, 12, figsize=(24, 24)) # 大画布适配12×12布局 axes_flat = axes.flatten() # 把二维轴数组转成一维,方便遍历 # 遍历前70个变量,绘制对应子图 for idx in range(70): ax = axes_flat[idx] # 绘制meanDf的时间序列趋势 ax.plot(time, meanDf.iloc[:, idx], label='Mean Trend', color='#1f77b4') # 标记warDf的最终反应结果 ax.scatter(time[-1], warDf.iloc[idx], label='Final Result', color='#ff4b5c', s=50) # 添加pcmean和ncmean的参考线 ax.axhline(y=pcmean, color='#2ca02c', linestyle='--', label='PC Mean') ax.axhline(y=ncmean, color='#ff7f0e', linestyle='--', label='NC Mean') # 调整子图细节,避免重叠 ax.set_title(f'Variable {idx+1}', fontsize=10) ax.legend(fontsize=8) ax.tick_params(axis='both', labelsize=8) # 批量隐藏剩余的空轴,一步搞定 for ax in axes_flat[70:]: ax.axis('off') plt.tight_layout() # 自动调整子图间距 plt.show()
方案二:动态计算行数,更紧凑的布局
如果你对12×12的严格布局没有硬性要求,只是想以12列为基准展示,那可以动态计算需要的行数(向上取整),这样画布不会过大,查看更紧凑:
import matplotlib.pyplot as plt import pandas as pd n_cols = 12 n_rows = (70 + n_cols - 1) // n_cols # 向上取整计算行数,70个图需要6行(6×12=72) fig, axes = plt.subplots(n_rows, n_cols, figsize=(24, n_rows*2)) axes_flat = axes.flatten() # 绘制逻辑和方案一完全一致 for idx in range(70): ax = axes_flat[idx] ax.plot(time, meanDf.iloc[:, idx], label='Mean Trend', color='#1f77b4') ax.scatter(time[-1], warDf.iloc[idx], label='Final Result', color='#ff4b5c', s=50) ax.axhline(y=pcmean, color='#2ca02c', linestyle='--', label='PC Mean') ax.axhline(y=ncmean, color='#ff7f0e', linestyle='--', label='NC Mean') ax.set_title(f'Variable {idx+1}', fontsize=10) ax.legend(fontsize=8) ax.tick_params(axis='both', labelsize=8) # 隐藏多余的2个空轴 for ax in axes_flat[70:]: ax.axis('off') plt.tight_layout() plt.show()
这两种方案都避免了繁琐的if-else判断,代码更简洁易维护,而且完全解决了索引越界的问题。你可以根据自己的布局偏好选择其中一种~
内容的提问来源于stack exchange,提问作者g pe
相关产品推荐
相关产品推荐

