【matplotlib】可视化解决方案——如何正确展示和保存图像

概述

在 matplotlib 实践中,很多情形下需要对输出图形进行指定路径的有效保存。这样输出图形就可以用于印刷或者其他形式的展示。因此本文就来介绍一下保存输出图形的方法。
一般情况下可以采用两种方式保存图像,第一种是在输出界面点击保存按钮;第二种是通过执行代码进行输出图形的保存。

示例

使用保存按钮进行保存

我们以下面的代码为例演示如何使用按钮保存图形。

import matplotlib.pyplot as plt  
import numpy as np  
  
plt.rcParams['axes.facecolor'] = "lemonchiffon"  
  
x = np.linspace(0, 2, 1000)  
y = 0.9 * np.sin(np.pi * x)  
fig, ax = plt.subplots(2, 3)  
  
# subplot(2,3,1)  
ax[0, 0].plot(x, y, lw=3, color="steelblue")  
ax[0, 0].spines["right"].set_visible(False)  
ax[0, 0].spines["top"].set_visible(False)  
  
# set left and bottom spines position  
ax[0, 0].spines["left"].set_position(("data", 0.5))  
ax[0, 0].spines["bottom"].set_position(("data", 1))  
  
# set tickline position of bottom and left spines  
ax[0, 0].xaxis.set_ticks_position("bottom")  
ax[0, 0].yaxis.set_ticks_position("left")  
ax[0, 0].set_ylim(-1, 1)  
  
# subplot(2,3,4)  
ax[1, 0].plot(x, y, lw=3, color="steelblue")  
ax[1, 0].spines["right"].set_color("none")  
ax[1, 0].spines["top"].set_color("none")  
  
# set left and bottom spines position  
ax[1, 0].spines["left"].set_position("zero")  
ax[1, 0].spines["bottom"].set_position("zero")  
  
# set tickline position of bottom and left spines  
ax[1, 0].xaxis.tick_bottom()  
ax[1, 0].yaxis.tick_left()  
ax[1, 0].set_ylim(-1, 1)  
  
# subplot(2,3,2)  
ax[0, 1].plot(x, y, lw=3, color="steelblue")  
ax[0, 1].spines["right"].set_visible(False)  
ax[0, 1].spines["top"].set_visible(False)  
  
# set left and bottom spines position  
ax[0, 1].spines["left"].set_position(("axes", 0.25))  
ax[0, 1].spines["bottom"].set_position(("axes", 0.75))  
  
# set tickline position of bottom and left spines  
ax[0, 1].xaxis.set_ticks_position("bottom")  
ax[0, 1].yaxis.set_ticks_position("left")  
ax[0, 1].set_ylim(-1, 1)  
  
# subplot(2,3,5)  
ax[1, 1].plot(x, y, lw=3, color="steelblue")  
  
ax[1, 1].spines["right"].set_color("none")  
ax[1, 1].spines["top"].set_color("none")  
ax[1, 1].spines["left"].set_position("center")  
  
# set left and bottom spines position  
ax[1, 1].spines["bottom"].set_position("center")  
  
# set tickline position of bottom and left spines  
ax[1, 1].xaxis.tick_bottom()  
ax[1, 1].yaxis.tick_left()  
ax[1, 1].set_ylim(-1, 1)  
  
# subplot(2,3,3)  
ax[0, 2].plot(x, y, lw=3, color="steelblue")  
ax[0, 2].spines["right"].set_visible(False)  
ax[0, 2].spines["top"].set_visible(False)  
  
# set leftandbottomspinespines position  
ax[0, 2].spines["left"].set_position(("outward", 3))  
ax[0, 2].spines["bottom"].set_position(("outward", 2))  
  
# set tickline position of bottom and left spines  
ax[0, 2].xaxis.set_ticks_position("bottom")  
ax[0, 2].yaxis.set_ticks_position("left")  
ax[0, 2].set_ylim(-1, 1)  
  
# subplot(2,3,6)  
ax[1, 2].plot(x, y, lw=3, color="steelblue")  
ax[1, 2].spines["right"].set_color("none")  
ax[1, 2].spines["top"].set_color("none")  
  
# set left and bottom spines position  
ax[1, 2].spines["left"].set_position(("outward", -3))  
ax[1, 2].spines["bottom"].set_position(("outward", -2))  
  
# set tickline position of bottom and left spines  
  
ax[1, 2].xaxis.tick_bottom()  
ax[1, 2].yaxis.tick_left()  
  
ax[1, 2].set_ylim(-1, 1)  
  
fig.subplots_adjust(wspace=0.35, hspace=0.2)  
plt.show()

画图结果如下:

画图结果

可以通过下图中红框位置的保存按钮进行保存。

使用保存按钮

保存支持的格式如下:

支持的格式

通过执行代码语句保存图形

通过执行代码语句保存图形其实很简单,依然以上面的代码为例,只需在代码的最后添加 plt.savefig("img.png") 就可以完成图片保存行为,完整代码如下:

import matplotlib.pyplot as plt  
import numpy as np  
  
plt.rcParams['axes.facecolor'] = "lemonchiffon"  
  
x = np.linspace(0, 2, 1000)  
y = 0.9 * np.sin(np.pi * x)  
fig, ax = plt.subplots(2, 3)  
  
# subplot(2,3,1)  
ax[0, 0].plot(x, y, lw=3, color="steelblue")  
ax[0, 0].spines["right"].set_visible(False)  
ax[0, 0].spines["top"].set_visible(False)  
  
# set left and bottom spines position  
ax[0, 0].spines["left"].set_position(("data", 0.5))  
ax[0, 0].spines["bottom"].set_position(("data", 1))  
  
# set tickline position of bottom and left spines  
ax[0, 0].xaxis.set_ticks_position("bottom")  
ax[0, 0].yaxis.set_ticks_position("left")  
ax[0, 0].set_ylim(-1, 1)  
  
# subplot(2,3,4)  
ax[1, 0].plot(x, y, lw=3, color="steelblue")  
ax[1, 0].spines["right"].set_color("none")  
ax[1, 0].spines["top"].set_color("none")  
  
# set left and bottom spines position  
ax[1, 0].spines["left"].set_position("zero")  
ax[1, 0].spines["bottom"].set_position("zero")  
  
# set tickline position of bottom and left spines  
ax[1, 0].xaxis.tick_bottom()  
ax[1, 0].yaxis.tick_left()  
ax[1, 0].set_ylim(-1, 1)  
  
# subplot(2,3,2)  
ax[0, 1].plot(x, y, lw=3, color="steelblue")  
ax[0, 1].spines["right"].set_visible(False)  
ax[0, 1].spines["top"].set_visible(False)  
  
# set left and bottom spines position  
ax[0, 1].spines["left"].set_position(("axes", 0.25))  
ax[0, 1].spines["bottom"].set_position(("axes", 0.75))  
  
# set tickline position of bottom and left spines  
ax[0, 1].xaxis.set_ticks_position("bottom")  
ax[0, 1].yaxis.set_ticks_position("left")  
ax[0, 1].set_ylim(-1, 1)  
  
# subplot(2,3,5)  
ax[1, 1].plot(x, y, lw=3, color="steelblue")  
  
ax[1, 1].spines["right"].set_color("none")  
ax[1, 1].spines["top"].set_color("none")  
ax[1, 1].spines["left"].set_position("center")  
  
# set left and bottom spines position  
ax[1, 1].spines["bottom"].set_position("center")  
  
# set tickline position of bottom and left spines  
ax[1, 1].xaxis.tick_bottom()  
ax[1, 1].yaxis.tick_left()  
ax[1, 1].set_ylim(-1, 1)  
  
# subplot(2,3,3)  
ax[0, 2].plot(x, y, lw=3, color="steelblue")  
ax[0, 2].spines["right"].set_visible(False)  
ax[0, 2].spines["top"].set_visible(False)  
  
# set leftandbottomspinespines position  
ax[0, 2].spines["left"].set_position(("outward", 3))  
ax[0, 2].spines["bottom"].set_position(("outward", 2))  
  
# set tickline position of bottom and left spines  
ax[0, 2].xaxis.set_ticks_position("bottom")  
ax[0, 2].yaxis.set_ticks_position("left")  
ax[0, 2].set_ylim(-1, 1)  
  
# subplot(2,3,6)  
ax[1, 2].plot(x, y, lw=3, color="steelblue")  
ax[1, 2].spines["right"].set_color("none")  
ax[1, 2].spines["top"].set_color("none")  
  
# set left and bottom spines position  
ax[1, 2].spines["left"].set_position(("outward", -3))  
ax[1, 2].spines["bottom"].set_position(("outward", -2))  
  
# set tickline position of bottom and left spines  
  
ax[1, 2].xaxis.tick_bottom()  
ax[1, 2].yaxis.tick_left()  
  
ax[1, 2].set_ylim(-1, 1)  
  
fig.subplots_adjust(wspace=0.35, hspace=0.2)  
  
plt.savefig("img.png")  
plt.show()

这里我们稍微深入研究一下 plt.savefig() 这个方法,它的源码分析如下:

def savefig(*args, **kwargs):  
    # 获取当前的Figure对象
    fig = gcf()  
    # 调用Figure对象的savefig方法
    res = fig.savefig(*args, **kwargs)  
    fig.canvas.draw_idle()   # need this if 'transparent=True' to reset colors  
    return res

从源码可以看到,matplotlib 只能以一个 Figure 对象为单位进行保存,所以不能将子图单独保存,这提醒我们在布局阶段就得想好是否对 Figure 对象划分子图;其次源码中的 Figure 对象是通过 gcf() 方法获取的,如果程序中有多个 Figure 对象,有可能保存这个行为和预期不符,建议在程序中不要调用 plt.savefig() 方法,而是使用面向对象的方式,调用 Figure.savefig() 进行图像保存。

除了传递图片名称(fname),savefig 方法还可以传递如下参数:

  • dpi:图像分辨率,默认和调用方法的 Figure 对象一致;
  • format:如果图片名称中没有指定格式,则使用该参数指定的格式保存图片;
  • metadata:图片元数据,该参数的行为取决于图像格式;
  • facecolor:指定保存图片的背景颜色;
  • edgecolor:指定保存图片的边缘颜色;

往期回顾

  1. 【matplotlib】可视化解决方案——如何设置字符串的输出字体效果
  2. 【matplotlib】可视化解决方案——如何正确使用颜色映射表
  3. 【matplotlib】可视化解决方案——如何调整轴脊位置
  4. 【matplotlib】可视化解决方案——如何设置坐标系计量方法
  5. 【matplotlib】可视化解决方案——如何正确使用文本注释
  6. 【matplotlib】可视化解决方案——如何调整计量单位和计量方法
  7. 【matplotlib】可视化解决方案——如何实现图形的动画效果
  8. 【matplotlib】可视化解决方案——如何正确使用plot方法
  9. 【matplotlib】可视化解决方案——如何向画布中添加坐标轴
  10. 【matplotlib】可视化解决方案——如何正确使用matplotlib颜色系统

文中难免会出现一些描述不当之处(尽管我已反复检查多次),欢迎在留言区指正,相关的知识点也可进行分享,希望大家都能有所收获!!如果觉得我的文章写得还行,不妨支持一下。你的每一个转发、关注、点赞、评论都是对我最大的支持!

©著作权归作者所有,转载或内容合作请联系作者
  • 序言:七十年代末,一起剥皮案震惊了整个滨河市,随后出现的几起案子,更是在滨河造成了极大的恐慌,老刑警刘岩,带你破解...
    沈念sama阅读 213,335评论 6 492
  • 序言:滨河连续发生了三起死亡事件,死亡现场离奇诡异,居然都是意外死亡,警方通过查阅死者的电脑和手机,发现死者居然都...
    沈念sama阅读 90,895评论 3 387
  • 文/潘晓璐 我一进店门,熙熙楼的掌柜王于贵愁眉苦脸地迎上来,“玉大人,你说我怎么就摊上这事。” “怎么了?”我有些...
    开封第一讲书人阅读 158,766评论 0 348
  • 文/不坏的土叔 我叫张陵,是天一观的道长。 经常有香客问我,道长,这世上最难降的妖魔是什么? 我笑而不...
    开封第一讲书人阅读 56,918评论 1 285
  • 正文 为了忘掉前任,我火速办了婚礼,结果婚礼上,老公的妹妹穿的比我还像新娘。我一直安慰自己,他们只是感情好,可当我...
    茶点故事阅读 66,042评论 6 385
  • 文/花漫 我一把揭开白布。 她就那样静静地躺着,像睡着了一般。 火红的嫁衣衬着肌肤如雪。 梳的纹丝不乱的头发上,一...
    开封第一讲书人阅读 50,169评论 1 291
  • 那天,我揣着相机与录音,去河边找鬼。 笑死,一个胖子当着我的面吹牛,可吹牛的内容都是我干的。 我是一名探鬼主播,决...
    沈念sama阅读 39,219评论 3 412
  • 文/苍兰香墨 我猛地睁开眼,长吁一口气:“原来是场噩梦啊……” “哼!你这毒妇竟也来了?” 一声冷哼从身侧响起,我...
    开封第一讲书人阅读 37,976评论 0 268
  • 序言:老挝万荣一对情侣失踪,失踪者是张志新(化名)和其女友刘颖,没想到半个月后,有当地人在树林里发现了一具尸体,经...
    沈念sama阅读 44,393评论 1 304
  • 正文 独居荒郊野岭守林人离奇死亡,尸身上长有42处带血的脓包…… 初始之章·张勋 以下内容为张勋视角 年9月15日...
    茶点故事阅读 36,711评论 2 328
  • 正文 我和宋清朗相恋三年,在试婚纱的时候发现自己被绿了。 大学时的朋友给我发了我未婚夫和他白月光在一起吃饭的照片。...
    茶点故事阅读 38,876评论 1 341
  • 序言:一个原本活蹦乱跳的男人离奇死亡,死状恐怖,灵堂内的尸体忽然破棺而出,到底是诈尸还是另有隐情,我是刑警宁泽,带...
    沈念sama阅读 34,562评论 4 336
  • 正文 年R本政府宣布,位于F岛的核电站,受9级特大地震影响,放射性物质发生泄漏。R本人自食恶果不足惜,却给世界环境...
    茶点故事阅读 40,193评论 3 317
  • 文/蒙蒙 一、第九天 我趴在偏房一处隐蔽的房顶上张望。 院中可真热闹,春花似锦、人声如沸。这庄子的主人今日做“春日...
    开封第一讲书人阅读 30,903评论 0 21
  • 文/苍兰香墨 我抬头看了看天上的太阳。三九已至,却和暖如春,着一层夹袄步出监牢的瞬间,已是汗流浃背。 一阵脚步声响...
    开封第一讲书人阅读 32,142评论 1 267
  • 我被黑心中介骗来泰国打工, 没想到刚下飞机就差点儿被人妖公主榨干…… 1. 我叫王不留,地道东北人。 一个月前我还...
    沈念sama阅读 46,699评论 2 362
  • 正文 我出身青楼,却偏偏与公主长得像,于是被迫代替她去往敌国和亲。 传闻我的和亲对象是个残疾皇子,可洞房花烛夜当晚...
    茶点故事阅读 43,764评论 2 351

推荐阅读更多精彩内容