为什么要学习matplotlib
- 能将数据进行可视化,更直观的呈现
- 使数据更加客观、更具说服力
matplotlib
:最流行的Python底层绘图库,主要做数据可视化图表,名字取材MATLAB
,模仿MATLAB
构建
matplotlib基本要点
每个红色的点是坐标,把5个点的坐标连接成一条线,组成了一个折线图。
示例:
假设一天中每隔两个小时(range(2, 25, 2))的气温(C)分别是[15, 13, 14.5, 17, 20, 25, 26, 26, 27, 22, 18, 15]
from matplotlib import pyplot as plt # 导入pyplot
x = range(2, 26, 2)
# 数据在x轴的位置,是一个可迭代对象
y = [15, 13, 14.5, 17, 20, 25, 26, 26, 24, 22, 18, 15]
# 数据在y轴的位置,是一个可迭代对象
# x轴和y轴的数据一起组成了所有要绘制出的坐标
# 分别是(2, 15), (4, 13), (6, 14.5), (8, 17)......
plt.plot(x, y) # 传入x和y,通过plot绘制出折线图
plt.show() # 在执行程序的时候展示图形
WE CAN DO MORE
但是目前存在以下几个问题:
- 设置图片大小(想要一个高清无码大图)
- 保存到本地
- 描述信息,比如x轴和y轴表示什么,这个图表示什么
- 调整x或者y的刻度的间距
- 线条的样式(比如颜色,透明度等)
- 标记出特殊的点(比如告诉别人最高点和最低点在哪里)
- 给图片添加一个水印(防伪,防止盗用)
设置图片大小
improt matplotlib.pyplot as plt
fig = plt.figure(figsize=(20, 8), dpi=80)
# figure图形图标的意思,在这里指的就是我们画的图
# 通过实例化一个figure并且传递参数,能够在后台自动使用该figure实例
# 在图像模糊的时候可以传入dpi参数,让图片更加清晰
x = range(2, 26, 2)
y = [15, 13, 14.5, 17, 20, 25, 26, 26, 24, 22, 18, 15]
plt.plot(x, y)
plt.savefig("./sig_size.png") # 保存图片 可以保存svg这种矢量图格式,放大不会有锯齿
plt.show()
调整x或者y轴上的刻度
import matplotlib.pylot as plt
fig = plt.figure(figsize(10, 5))
x = range(2, 26, 2)
y = [15, 13, 14.5, 17, 20, 25, 26, 26, 24, 22, 18, 15]
plt.plot(x, y)
plt.xticks(x) # 设置x的刻度
# plt.xticks(x[::2])
# 当刻度太密集的时候使用列表的步长(间隔取值)来解决,matplotlib自动帮我们对应plt.show()
设置中文显示
为什么无法显示中文:
matplotlib
默认不支持中文字符,因为默认的英文字体无法显示汉字
查看linux/mac
下面支持的字符:
fc-list
-> 查看支持的字体
fc-list: lang-zh
-> 查看支持的中文(冒号前面有空格)
如何修该matplotlib的默认字体?
通过matplotlib.rc
可以修改,具体方法参见源码(windown/linux)
通过matplotlib
下的font manager
可以解决(window/linux/mac)
示例代码1:
from matplotlib import pyplot as plt
import matplotlib
import random
font = {
'family': 'MicroSoft YaHei',
'weight': 'bold',
'size': 10,
}
matplotlib.rc("font", **font)
fig = plt.figure(figsize=(10, 5))
x = range(0, 120)
y = [random.randint(20, 35) for i in range(0, 120)]
# 取步长,数字与字符串一一对应,数据长度一眼
x_lable = ["10点{0:>02}分".format(i) for i in range(0, 60)]
x_lable = x_lable + ["11点{0:>02}分".format(i) for i in range(0, 60)]
plt.plot(x, y)
plt.xticks(x[::5], x_lable[::5], rotation=45) # ratation旋转角度
plt.show()
示例代码2:
from matplotlib import pyplot as plt
from matplotlib import font_manager
# import matplotlib
import random
my_font = font_manager.FontProperties(fname="C:\\Windows\\Fonts\\s8514sys.fon")
fig = plt.figure(figsize=(10, 5))
x = range(0, 120)
y = [random.randint(20, 35) for i in range(0, 120)]
x_lable = ["10点{0:>02}分".format(i) for i in range(0, 60)]
x_lable = x_lable + ["11点{0:>02}分".format(i) for i in range(0, 60)]
# 取步长,数字与字符串一一对应,数据长度一眼
plt.plot(x, y)
plt.xticks(x[::5], x_lable[::5], rotation=45, font_properties=my_font)
plt.show()
给图像添加描述信息
from matplotlib import pyplot as plt
import random
font = {
'family': 'MicroSoft YaHei',
'weight': 'bold',
'size': 10,
}
matplotlib.rc("font", **font)
fig = plt.figure(figsize=(10, 5))
x = range(0, 120)
y = [random.randint(20, 35) for i in range(0, 120)]
# 取步长,数字与字符串一一对应,数据长度一眼
x_lable = ["10点{0:>02}分".format(i) for i in range(0, 60)]
x_lable = x_lable + ["11点{0:>02}分".format(i) for i in range(0, 60)]
plt.rcParams['font.sans-serif'] = ['SimHei'] # 用来正常显示中文标签
plt.rcParams['axes.unicode_minus'] = ['SimHei'] # 用来正常显示负号
plt.plot(x, y)
plt.xticks(x[::5], x_lable[::5], rotation=45) # ratation旋转角度
plt.xlabel("时间")
plt.ylabel("温度(度)")
plt.title("10到12点每分钟的时间变化请求")
plt.show()
自定义绘制图形的风格
plt.grid(alpha=0.4) # 绘制网格
plt.legend(prop=my_font, loc="upper left") # 添加图例
plt.plot(
x, # x
y, # y
->在绘制的时候指定即可
color='r' # 线条颜色
linestyle='--', # 线条风格
linewidth=5, # 线条粗细
alpha=0.5, # 透明度
)
颜色字符 | 风格字符 |
---|---|
r 红色 |
- 实线 |
g 绿色 |
-- 虚线、破折线 |
b 蓝色 |
-. 点划线 |
w 白色 |
: 点虚线、虚线 |
-- | ''留空或空格,无线条 |
c 青色 |
-- |
m 洋红 |
-- |
y 黄色 |
-- |
k 黑色 |
-- |
-- | -- |
#00ff00 16进制 |
-- |
0.8 灰度值字符串 |
-- |
对比常用统计图
折线图:以折线的上升或下降来表示统计数量的增减变化的统计图特点::能够显示数据的变化趋势,反映事物的变化情况。(变化)
直方图:由一系列高度不等的纵向条纹或线段表示数据分布的情况。一般用横轴表示数据范围,纵轴表示分布情况。
特点::绘制连续性的数据,展示一组或者多组数据的分布状况(统计)
条形图:排列在工作表的列或行中的数据可以绘制到条形图
特点::绘制连离散的数据,能够一眼看出各个数据的大小,比较数据之间的差别(统计)
散点图:用两组数据构成多个坐标点,考察坐标点的分布,判断两变量之间是否存在某种关联或总结坐标点的分布模式。
特点::判断变量之间是否存在数量关联趋势,展示离群点(分布规律)
散点图
示例代码:
from matplotlib import pyplot as plt
y_3 = [11, 17, 16, 11, 12, 11, 12, 6, 6, 7, 8, 9, 12, 15, 14, 17, 18, 21, 16, 17, 20, 14, 15, 19, 21, 22, 22, 22, 23, 24]
y_10 = [26, 26, 28, 19, 21, 17, 16, 19, 18, 20, 20, 19, 22, 23, 17, 20, 21, 20, 22, 15, 5, 13, 17, 10, 11, 13, 12, 13, 6, 7]
x_3 = range(1, 31)
x_10 = range(41, 71)
plt.rcParams["font.sans-serif"] = ['SimHei']
plt.figure(figsize=(15, 8), dpi=80)
plt.scatter(x_3, y_3, label="3月份")
plt.scatter(x_10, y_10, label="10月份")
_x = list(x_3)+list(x_10)
plt.xticks(_x[::3], ([f"3月{i}日" for i in x_3] + [f"10月{i-40}日" for i in x_10])[::3], rotation=45)
plt.legend()
plt.xlabel("日期")
plt.ylabel("温度")
plt.title("3月份和10月份温度分布走势图")
plt.savefig("..")
plt.show()
条形图
示例代码:
from matplotlib import pyplot as plt
plt.rcParams["font.sans-serif"] = ["SimHei"]
a = ["猩球崛起3:终极之战", "敦刻尔克", "蜘蛛侠:英雄归来", "战狼2"]
b_16 = [15746, 321, 4497, 219]
b_15 = [12357, 156, 2045, 168]
b_14 = [2358, 399, 2358, 362]
bar_width = 0.2
x_15 = [i+bar_width for i in range(len(a))]
x_16 = [i+bar_width*2 for i in range(len(a))]
plt.figure(figsize=(10, 5))
plt.barh(range(len(a)), b_14, height=bar_width, label="9月14日")
plt.barh(x_15, b_15, height=bar_width, label="9月15日")
plt.barh(x_16, b_16, height=bar_width, label="9月16日")
plt.yticks([i+bar_width for i in range(len(a))], a)
plt.legend()
plt.show()
直方图
把数据分为多少组进行统计??
组数要适当,太少会有较大的统计误差,太多规律不明显
组数:将数据分组,当数据在100个以内时,按数据多少常分5-12组。
组距:指每个小组的两个端点的距离。
组数 = 极差/组距 = (max(a)-min(a))/ bin_width
bin_width = 3 #设置组距为3
num_bins = int((max(a)-min(a))/bin_width) # 分为多少组
plt.hist(a, num_bins) # 传入需要统计的数据,以及组数即可
# plt.hist(a, [min(a)+i*bin_width for i in range(num_bins)])
# 可以传入一个列表,长度为组数,值为分组依据,当组距不均匀的时候使用
# plt.hist(a, num_bins, normed=1)
# normed:bool 是否绘制频率分布直方图,默认为频数直方图
plt.xticks(list(range(min(a), max(a)))[::bin_width], rotation=45)
plt.grid(True, linestyle="-.", alpha=0.5) # 显示网格,alpha为透明度