import matplotlib.pyplot as plt
%matplotlib inline
import seaborn as sb
matplotlib能高度兼容numpy与pandas数据结构以及scipy与statsmodels等统计模块
Seaborn作为matplotlib的补充,在matplotlib的基础上进行了更高级的API封装,从而使得作图更加容易
Tableau凭借其强大的数据可视化的功能成为硅谷炙手可热的上市公司。其理论基础其实是《The Grammar of Graphic》
ggplot:R语言上的一个图形库
一、总纲
- 设计原则
-
流程
数据分析流程
- 提取
数据来源:问卷调查,数据库,网络或其他数据源- 清洗
+处理缺失值
+确定要保留的数据的列
+对数据进行四舍五入
…………- 探索数据
- 分析
预测销售额,欺诈等- 分享
- 要素
- 颜色
在散点图中增加类别,最合适的视觉编码
首选黑白色:许多情况下,黑、白以及灰色阴影足够表达信息
选择天然色或淡色,尽量少使用强烈的颜色
在鲜艳的颜色中加入灰色:使颜色看起来更柔和(感觉更柔和)
彩虹色,三原色以及其他鲜艳的亮色增加噪点(转移注意力),刺激眼睛
@针对色盲
应该使用蓝橙,避免在可视化中使用红绿这两种颜色来做数据之间的区分
或者利用其他可视化元素,比如形状、位置或者亮度- 位置变化
最敏感的视觉编码,比如:散点图中 x/y 坐标位置的变化- 长度变化
比如:条形图和直方图的条形高度变化- 色调(不敏感)
比如用了较多颜色的散点图- 面积变化(不敏感)
比如饼状图- 图表垃圾
不需要或冗余的可视化元素- 高数据墨水比
使可视化呈现高价值- 诚实设计
失真系数(Lie factor):比例变化
- 数据类型
- 分类Categorical(文本标记)
- 无序分类变量(Nominal data)
有序分类变量(Ordinal data)
特殊:李克特量表(Likert Scale),本质上被认为是有序分类变量,简化起见,经常会被视作是定距数据 李克特量表
- 数值(Numeric)类型(又称定量类型)
离散型
连续型
- 定距变量(Interval data)
绝对差有意义的数值型数据(可以进行加减运算)
有零点:绝对温度;公元0年
注意:10°是5°的两倍,不能说比5°热两倍- 定比变量(Ratio data)
相对差有意义的数值型数据(还可以进行乘除运算)
@长度单位:米制
@电流单位:安培
-
额外编码
只有在绝对必要时才使用这些额外的编码,减少信息负载
颜色与形状是分类变量最好的展现方式
标志大小有助于数值型数据的表达 -
整洁的数据集
每种观察单位是一个表格(Each type of observational unit is a table) 整洁的数据表 不整洁的数据表
每个变量占一列(Each variable is a column)
每个观察值占一行(Each observation is a row)
二、单变量
提纲
plt.plot(x, y)
@matlab plot(x,y)
- 条形图(类别变量)
sb.countplot()
sb.barplot()
sb.pointplot()
- 饼图(类别变量)
plt.pie()
- 直方图(数值变量)
plt.hist()
sb.distplot()
1. 条形图bar chart (柱形图、柱状图)
base_color = sb.color_palette()[0] #返回一个 RGB 元组列表
df.value_counts() #统计排序
sb.countplot(data = df, x = 'cat_var', color = base_color)
#data: 数据集
#如果数据是pd.Series、一维NumPy 数组或列表形式:设为 countplot 函数的第一个参数
#x: 目标列
#y=目标列 改为横向条形图
seaborn.barplot(x=None, y=None, hue=None, data=None, order=None,
hue_order=None, estimator=<function mean>, ci=95, n_boot=1000,
units=None, orient=None, color=None, palette=None, saturation=0.75,
errcolor='.26', errwidth=None, capsize=None, dodge=True, ax=None,
**kwargs)
#将点估计和置信区间显示为柱形
#参数ci: float 或者 “sd” or None,float就是设定置信区间,sd就是描绘标准误差,如果为none就不会绘制误差线
#参数capsize:误差线上的横线的宽度
#参数errcolor :误差线颜色
#参数errwidth:误差线宽度
#参数estimator:估计误差的方法,默认是平均数+方差,也可以设置为中位数+方差
#给每一个长条标注文本
for loc, label in zip(locs, labels):
#获取条形图 x轴的类别名称
count = cat_counts[label.get_text()]
#基于格式控制 得到每个长条的文本(相对频率的百分数)
pct_string ='{:0.1f}%'.format(100*count/n_points)
#给长条 添加文本
plt.text(loc, count-8, pct_string, ha ='center', color = 'w')
默认:每个类别都用不同的颜色标注
条形图
- 针对有序的分类
level_order = ['Alpha', 'Beta', 'Gamma', 'Delta']
ordered_cat = pd.api.types.CategoricalDtype(ordered = True, categories = level_order)
df['cat_var'] = df['cat_var'].astype(ordered_cat)
- 针对无序分类数据
常见操作:按照频率对数据排序
base_color = sb.color_palette()[0]
cat_order = df['cat_var'].value_counts().index
sb.countplot(data = df, x = 'cat_var', color = base_color, order = cat_order)
- 针对其他数据
比如pd.Series或一维ndarray
sb.countplot(ndarray)
- 变式:相对频率
方法1:仅更改坐标轴刻度为相对比例
plt.yticks()
图形属性设置
方法2:在长条上使用文本注释标记相对频率
plt.text()
获取文本:.get_text() 返回字符串
- 补充实现方式
sb.barplot()
数据经过了汇总统计
sb.countplot()
数据尚未汇总
2. 饼图
需要数据为汇总的形式,函数的主要参数是扇区大小
最好只包含两到三个扇区;分类太多,则使用 "其他" 类别
通常选择条形图更保险
sorted_counts = df['cat_var'].value_counts()
plt.pie(sorted_counts, labels = sorted_counts.index, startangle = 90,
counterclock = False)
#参数wedgeprops:中间设置为空心
plt.pie(x, explode=None, labels=None, colors=None,
autopct=None, pctdistance=0.6,
shadow=False, labeldistance=1.1,
startangle=None, radius=None,
counterclock=True, wedgeprops=None,
textprops=None, center=(0, 0), frame=False,
rotatelabels=False, hold=None, data=None)
#每个部分的分数面积由x / sum(x)给出
#各个部分是逆时针绘制的,默认从x轴开始。
#必选参数x是Series数据
3. 直方图
plt.hist(data = df, x = 'num_var')
#bin_edges 序列:分组上下限+间距
plt.hist(x, bins=None, range=None, density=None,
weights=None, cumulative=False, bottom=None, histtype='bar',
align='mid', orientation='vertical', rwidth=None, log=False,
color=None, label=None, stacked=False, normed=None, hold=None,
data=None, **kwargs)
#如果输入包含多个数据,则返回值是一个元组(n,bin,patches)
#参数x :唯一一个必选参数,表示输入的数据,np的array或者pd的series,dataframe都可以
#参数bin : 整数或序列(列表或者array等等都可以),是可选的。整数的话,就是整数个柱子;序列的话,就是给出的序列作为柱子的边缘,比如[1,2,3,4],那么第一个柱子 (包括1,但不包括2),依次类推,共有3个,分别是,[1, 2)[2, 3)[3, 4],序列呢,就是可以设置的不那么平均了。
#参数rwidth: 柱体间隔,间隔空隙暗示值是离散的
#参数range:元组或None决定了bin的上限和下限。较低和较高的异常值将被忽略。(x.min(), x.max())(如果设置了bins为一个序列的话,那么range会无效)
#参数density:布尔型 如果设置为True,会让返回的n的值相加为1。决定的是每个格子频率占总数的百分比。
#参数cumulative:布尔型 如果设置为True,图表就变成了累积型,返回的n也是变成累加的值,而不是原来那种只有自己的值,确切来说,是后面的一个bin是前面的bin的值加上自己的值。
#参数weights:n或者是序列,是一组与x形状相同的权重,当然,如果density设为True,weights不生效
sb.distplot(df['num_var'])
#参数kde_kws
sb.distplot(a, bins=None, hist=True, kde=True, rug=False, fit=None,
hist_kws=None, kde_kws=None, rug_kws=None, fit_kws=None, color=None,
vertical=False, norm_hist=False, axlabel=None, label=None, ax=None)
#参数a:必须为Series, 1d-array, 或者 list.不像matplotlib.pyplot.hist那样,第一个数据可以是dataframe
#参数hist=True, kde=True,特别注意下,这两个参数默认为True
#参数rug是指轴须图,每根须都对应着一个数据,数据密了自然就粗了
默认含概率密度曲线:曲线下方的面积应该等于 1
带宽太小的话,数据看起来比实际的噪点更多,带宽太大的话,可能会遮蔽数据的有用特征 直方图 包含密度分布
纵轴表示的是数据密度,而不是直接的概率
通过 KDE 做出具体的概率判断没有直方图直观,但是使用核密度估计依然存在一定的理由。如果数据点相对较少,则 KDE 可以对整体数据分布提供平滑的估计
这些信息可能无法通过直方图轻松地呈现出来,大量的不连续跳跃性数据,在直方图中可能会造成误导。
KDE 中的带宽参数(bandwidth)会指定密度块体的宽度是多少
针对连续数据
注意分组间距的设置
针对离散数据
直方图或条形图都是可能的选择
直方图可能是最直接的选择,因为数据是数值型的,但是需要特别考虑一下分组边界的问题。因为离散型数值都是特定的值,而你的读者可能并不了解分组边界的值属于右边的分组,所以将分组边界设置为实际的两个值之间可以减少歧义 直方图:针对离散型数据
- 改进:长条不相连的直方图
plt.hist(die_rolls, bins = bin_edges, rwidth = 0.7)
#rwidth 直方图长条占各自宽度的比例
网友评论