datawhale可视化学习第三回:布局格式定方圆学习

import numpy as np
import pandas as pd
import matplotlib.pyplot as plt
plt.rcParams['font.sans-serif'] = ['SimHei']
plt.rcParams['axes.unicode_minus'] = False

这里的plt.rcParams是什么?

简单理解,这是自定义图形的各种默认属性。第一句是吧字体设置为’SimHei’由此可以显示中文,第二个就是可以解决x轴和y轴‘-’字符显示问题

但是这里又有个坑,由于SimHei是win自带的字体。所以mac的电脑这样设置是没用的,还是显示不了字符。

在这里插入图片描述

这时应该使用mac自带的字体,就可以了。

在这里插入图片描述

rc参数修改参考

绘图基本设置

一、子图

1. 使用 plt.subplots 绘制均匀状态下的子图

返回元素分别是画布和子图构成的列表,第一个数字为行,第二个为列

figsize 参数可以指定整个画布的大小

sharexsharey 分别表示是否共享横轴和纵轴刻度

tight_layout 函数可以调整子图的相对大小使字符不会重叠

fig, axs = plt.subplots(2, 5, figsize=(10, 4), sharex=True, sharey=True)
fig.suptitle('样例1', size=20,horizontalalignment='right',verticalalignment='center',x=0,y=1)
np.random.seed(0)
for i in range(2):
    for j in range(5):
        axs[i][j].scatter(np.random.randn(10), np.random.randn(10))
        axs[i][j].set_title('第%d行,第%d列'%(i+1,j+1))
        axs[i][j].set_xlim(-5,5)
        axs[i][j].set_ylim(-5,5)
        if i==1: axs[i][j].set_xlabel('横坐标')
        if j==0: axs[i][j].set_ylabel('纵坐标')
fig.tight_layout()
plt.show()

在这里插入图片描述

plt.suptitle()可以传入x=,y=来控制suptitle的位置。

horizontalalignment与verticalalignment是调整suptitle与坐标的相对位置。

如果horizontalalignment=right,那么就是文本标题的最右边在(x,y)位置上,horizontalalignment=center,就是文本标题的中间位置处于(x,y)

2.极坐标

除了常规的直角坐标系,也可以通过projection方法创建极坐标系下的图表

N = 150
r = 2 * np.random.rand(N)
theta = 2 * np.pi * np.random.rand(N)
area = 200 * r**2
colors = theta
plt.subplot(projection='polar')
plt.scatter(theta, r, c=colors, s=area, cmap='hsv', alpha=0.75)

在这里插入图片描述

这个图有点高阶。我们先看下极坐标的定义。

在平面内取一个定点O,叫极点,引一条射线Ox,叫做极轴,再选定一个长度单位和角度的正方向(通常取逆时针方向)。对于平面内任何一点M,用ρ表示线段OM的长度(有时也用r表示),θ表示从OX到OM的角度,ρ叫做点M的极径,θ叫做点M的极角,有序数对 (ρ,θ)就叫点M的极坐标,这样建立的坐标系叫做极坐标系。
在这里插入图片描述

import matplotlib.pyplot as plt
ax1 = plt.subplot(121, projection='polar')
ax2 = plt.subplot(122)
# 极坐标下需要的数据有极径和角度
r = np.arange(1,6,1)  # 极径
theta = [i*np.pi/2 for i in range(5)]  #角度
# 指定画图坐标为极坐标,projection='polar'
ax = plt.subplot(111, projection='polar')
ax.scatter(theta,r,linewidth=3,color='r')
# 加网格
ax.grid(True)
plt.show()

在这里插入图片描述

可以看到每个点都被标在相应的位置,只是坐标是(ρ,θ)

这里的1,2,3,4,5是网格线的极径值列表,最小值不能小于等于0。

在这里插入图片描述

具体参数设置参考

3. 使用 GridSpec 绘制非均匀子图

所谓非均匀包含两层含义,第一是指图的比例大小不同但没有跨行或跨列,第二是指图为跨列或跨行状态

利用 add_gridspec 可以指定相对宽度比例 width_ratios 和相对高度比例参数 height_ratios

fig = plt.figure(figsize=(10, 4))
spec = fig.add_gridspec(nrows=2, ncols=5, width_ratios=[1,2,3,4,5], height_ratios=[1,3])
fig.suptitle('样例2', size=20)
for i in range(2):
    for j in range(5):
        ax = fig.add_subplot(spec[i, j])
        ax.scatter(np.random.randn(10), np.random.randn(10))
        ax.set_title('第%d行,第%d列'%(i+1,j+1))
        if i==1: ax.set_xlabel('横坐标')
        if j==0: ax.set_ylabel('纵坐标')
fig.tight_layout()

在这里插入图片描述

注意:非均匀子图与均匀子图的写法有些许不同,非均匀状态子图是先fig.add_gridspec()作出非均匀子图,这是一个,然后fig.add_subplot()将primitives存入axes容器中。

在上面的例子中出现了 spec[i, j] 的用法,事实上通过切片就可以实现子图的合并而达到跨图的共能

fig = plt.figure(figsize=(10, 4))
spec = fig.add_gridspec(nrows=2, ncols=6, width_ratios=[2,2.5,3,1,1.5,2], height_ratios=[1,2])
fig.suptitle('样例3', size=20,x=-0.05,y=1)
# sub1
ax = fig.add_subplot(spec[0, :3])
ax.scatter(np.random.randn(10), np.random.randn(10))
# sub2
ax = fig.add_subplot(spec[0, 3:5])
ax.scatter(np.random.randn(10), np.random.randn(10))
# sub3
ax = fig.add_subplot(spec[:, 5])
ax.scatter(np.random.randn(10), np.random.randn(10))
# sub4
ax = fig.add_subplot(spec[1, 0])
ax.scatter(np.random.randn(10), np.random.randn(10))
# sub5
ax = fig.add_subplot(spec[1, 1:5])
ax.scatter(np.random.randn(10), np.random.randn(10))
fig.tight_layout()

在这里插入图片描述

这里的切片就是切fig.add_gridspec()的width_ratios和height_ratios参数。spec[i,j]里i是对height_ratios切片,j是对width_ratios切片。

举个例子sub1与sub2的width宽度比是(2+2.5+3):(1+1.5)即3:1

注意:在一个fig下每个spec切片的索引不能相交,其实可以理解为把一个大的画布进行不均等分割。

二、子图上的方法

ax 对象上定义了和 plt 类似的图形绘制函数,常用的有: plot, hist, scatter, bar, barh, pie

在这里插入图片描述

在这里插入图片描述

常用直线的画法为: axhline, axvline, axline (水平、垂直、任意方向)

在这里插入图片描述

ax.hline()添加一个水平线,第一个参数是与水平线垂直的值。第二个第三个参数是xmin和xmax,即与线平行的轴的值。

ax.vline()与其类似。

ax.axline()的参数可以看成两个坐标,然后相连。

使用 grid 可以加灰色网格

在这里插入图片描述

使用 set_xscale, set_title, set_xlabel 分别可以设置坐标轴的规度(指对数坐标等)、标题、轴名

在这里插入图片描述

.set_yscale(‘log’)是把y轴设置为对数坐标。

与一般的 plt 方法类似, legend, annotate, arrow, text 对象也可以进行相应的绘制

fig, ax = plt.subplots()
ax.arrow(0, 0, 1, 1, head_width=0.03, head_length=0.05, facecolor='red', edgecolor='blue')
ax.text(x=0, y=0,s='这是一段文字', fontsize=16, rotation=70, rotation_mode='anchor', color='green')
ax.annotate('这是中点', xy=(0.5, 0.5), xytext=(0.8, 0.2), arrowprops=dict(facecolor='yellow', edgecolor='black'), fontsize=16)

在这里插入图片描述

ax.arrow(x, y, dx, dy, **kwargs)

x,y是起始坐标,dx与dy是起始坐标的偏移量,head_width控制箭头宽度。

ax.text(x, y, s, fontdict=None, **kwargs) 在axes中加入文本。

x,y是文字的坐标(应该是text的开头坐标),fontdict是改变text的属性。

ax.annotate(text, xy, *args, **kwargs) 对某点添加注释。

text传入注释的文本,xy是注释点的坐标,xytest是注释文本的坐标。注意这里xy与xytest是用元组传入坐标。

fig, ax = plt.subplots()
ax.plot([1,2],[2,1],label="line1")
ax.plot([1,1],[1,2],label="line1")
ax.legend(loc=1)

在这里插入图片描述

其中,图例的 loc 参数如下:

stringcode
best0
upper right1
upper left2
lower left3
lower right4
right5
center left6
center right7
lower center8
upper center9
center10

三、作业

1. 墨尔本1981年至1990年的每月温度情况

from matplotlib.pyplot import MultipleLocator
import numpy as np
import pandas as pd 
import matplotlib.pyplot as plt
ex1 = pd.read_csv('data/layout_ex1.csv')
fig, axs = plt.subplots(2, 5, figsize=(16, 4),sharex=True, sharey=True)
fig.suptitle('墨尔本1981年至1990年月温度曲线', size=15,horizontalalignment='right',verticalalignment='center',x=0.55,y=1)
index_1=pd.Series(range(0,121,12))
for i in range(2):
    for j in range(5):
        axs[i][j].plot(range(1,13),ex1['Temperature'][index_1[i*5+j]:index_1[i*5+j+1]],marker='*')
        axs[i][j].set_xlim(0.5,12.5)
        axs[i][j].set_ylim(4,20)
        axs[i][j].set_title('%d年'%(1981+5*i+j),size=10)
        if j==0:axs[i][j].set_ylabel('气温')
        x_major_locator=MultipleLocator(1)
        axs[i][j].xaxis.set_major_locator(x_major_locator)
        
fig.tight_layout()
plt.show()

在这里插入图片描述

2. 画出数据的散点图和边际分布

  • np.random.randn(2, 150) 生成一组二维数据,使用两种非均匀子图的分割方法,做出该数据对应的散点图和边际分布图
import pandas as pd 
import matplotlib.pyplot as plt
import numpy as np
np.random.seed(22)
X=np.random.randn(2,150)
fig = plt.figure(figsize=(6,6))
spec = fig.add_gridspec(nrows=2, ncols=2, width_ratios=[4,1], height_ratios=[1,4])
for i in range(2):
    for j in range(2):
        if (i==0)&(j==1):
            continue
        ax=fig.add_subplot(spec[i,j])
        if (i ==1) & (j==0):
            ax.scatter(X[0],X[1])
            ax.set_xlabel('my_data_x')
            ax.set_ylabel('my_data_y')
            ax.grid(True)
        if (i==0)&(j==0):
            ax.hist(X[0],rwidth=0.9)  #设置柱子的宽度占bins宽的比例,可以理解为调整柱子的宽度
            ax.xaxis.set_major_locator(plt.NullLocator()) #去掉双轴
            ax.yaxis.set_major_locator(plt.NullLocator())
            ax.axis('off')  #去掉外面的框
        if (i==1)&(j==1):
            ax.hist(X[1],orientation='horizontal',rwidth=[0.9])
            ax.xaxis.set_major_locator(plt.NullLocator())
            ax.yaxis.set_major_locator(plt.NullLocator())
            ax.axis('off')
fig.suptitle('习题2-解法1', size=20)
fig.tight_layout()
plt.show()

在这里插入图片描述

import numpy as np
import pandas as pd 
import matplotlib.pyplot as plt
np.random.seed(22)
X=np.random.randn(2,150)
fig = plt.figure(figsize=(6,6))
spec = fig.add_gridspec(nrows=2, ncols=2, width_ratios=[4,1], height_ratios=[1,4])
ax = fig.add_subplot(spec[0,:1])
ax.hist(X[0],rwidth=0.8)
ax.xaxis.set_major_locator(plt.NullLocator()) #去掉双轴
ax.yaxis.set_major_locator(plt.NullLocator())
ax.axis('off')  #去掉外面的框
ax = fig.add_subplot(spec[1,:1])
ax.scatter(X[0],X[1])
ax.set_xlabel('my_data_x')
ax.set_ylabel('my_data_y')
ax.grid(True)
ax = fig.add_subplot(spec[1,1:])
ax.hist(X[0],rwidth=0.8,orientation='horizontal')
ax.xaxis.set_major_locator(plt.NullLocator()) #去掉双轴
ax.yaxis.set_major_locator(plt.NullLocator())
ax.axis('off')
fig.tight_layout()

在这里插入图片描述

  • 0
    点赞
  • 1
    收藏
    觉得还不错? 一键收藏
  • 1
    评论
评论 1
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值