
作者 | 刘顺祥
来源 | 数据分析1480
在《Python数据清洗(一):类型转换和冗余数据删除》和《Python数据清洗(二):缺失值识别与处理》文中已经讲解了有关数据中重复观测和缺失值的识别与处理,在本节中将分享异常值的判断和处理方法。
异常值也称为离群点,就是那些远离绝大多数样本点的特殊群体,通常这样的数据点在数据集中都表现出不合理的特性。如果忽视这些异常值,在某些建模场景下就会导致结论的错误(如线性回归模型、K均值聚类等),所以在数据的探索过程中,有必要识别出这些异常值并处理好它们。
异常值的识别
通常,异常值的识别可以借助于图形法(如箱线图、正态分布图)和建模法(如线性回归、聚类算法、K近邻算法),在本期内容中,将分享两种图形法,在下一期将分享基于模型识别异常值的方法。
箱线图法
箱线图技术实际上就是利用数据的分位数识别其中的异常点,该图形属于典型的统计图形,在学术界和工业界都得到广泛的应用。箱线图的形状特征如下图所示:
图中的下四分位数指的是数据的25%分位点所对应的值(Q1);中位数即为数据的50%分位点所对应的值(Q2);上四分位数则为数据的75%分位点所对应的值(Q3);上须的计算公式为Q3+1.5(Q3-Q1);下须的计算公式为Q1-1.5(Q3-Q1)。其中,Q3-Q1表示四分位差。如果采用箱线图识别异常值,其判断标准是,当变量的数据值大于箱线图的上须或者小于箱线图的下须时,就可以认为这样的数据点为异常点。
所以,基于上方的箱线图,可以定义某个数值型变量中的异常点和极端异常点,它们的判断表达式如下表所示:
在Python中可以使用matplotlib模块实现数据的可视化,其中boxplot函数就是用于绘制箱线图的。下面以1700年至1988年太阳黑子数量的数据为例,利用箱线图法识别数据中的异常点和极端异常点。具体的代码如下:
# 导入第三方模块 import pandas as pd import matplotlib.pyplot as plt # 导入数据 sunspots = pd.read_csv(r'C:\Users\Administrator\Desktop\sunspots.csv') # 绘制箱线图(1.5倍的四分位差,如需绘制3倍的四分位差,只需调整whis参数) plt.boxplot(x = sunspots.counts, # 指定绘制箱线图的数据 whis = 1.5, # 指定1.5倍的四分位差 widths = 0.7, # 指定箱线图的宽度为0.8 patch_artist = True, # 指定需要填充箱体颜色 showmeans = True, # 指定需要显示均值 boxprops = {'facecolor':'steelblue'}, # 指定箱体的填充色为铁蓝色 # 指定异常点的填充色、边框色和大小 flierprops = {'markerfacecolor':'red', 'markeredgecolor':'red', 'markersize':4}, # 指定均值点的标记符号(菱形)、填充色和大小 meanprops = {'marker':'D','markerfacecolor':'black', 'markersize':4}, medianprops = {'linestyle':'--','color':'orange'}, # 指定中位数的标记符号(虚线)和颜色 labels = [''] # 去除箱线图的x轴刻度值 ) # 显示图形 plt.show()
如上图所示,利用matplotlib子模块pyplot中的boxplot函数可以非常方便地绘制箱线图,其中左图的上下须设定为1.5倍的四分位差,右图的上下须设定为3倍的四分位差。从左图可知,发现数据集中至少存在5个异常点,它们均在上须之上;而在右图中并没有显示极端异常点。
通过上图可以直观地发现数据中是否存在异常点或极端异常点,但无法得知哪些观测为异常点,以及这些异常点的具体数值。为解决该问题,读者可以通过下方的代码实现查询:
# 计算下四分位数和上四分位 Q1 = sunspots.counts.quantile(q = 0.25) Q3 = sunspots.counts.quantile(q = 0.75) # 基于1.5倍的四分位差计算上下须对应的值 low_whisker = Q1 - 1.5*(Q3 - Q1) up_whisker = Q3 + 1.5*(Q3 - Q1) # 寻找异常点 sunspots.counts[(sunspots.counts > up_whisker) | (sunspots.counts < low_whisker)]
正态分布图法
根据正态分布的定义可知,数据点落在偏离均值正负1倍标准差(即sigma值)内的概率为68.2%;数据点落在偏离均值正负2倍标准差内的概率为95.4%;数据点落在偏离均值正负3倍标准差内的概率为99.6%。
所以,换个角度思考上文提到的概率值,如果数据点落在偏离均值正负2倍标准差之外的概率就不足5%,它属于小概率事件,即认为这样的数据点为异常点。同理,如果数据点落在偏离均值正负3倍标准差之外的概率将会更小,可以认为这些数据点为极端异常点。为使读者直观地理解文中提到的概率值,可以查看标准正态分布的概率密度图,如下图所示:
进一步,基于上图的结论,可以按照下表中的判断条件,识别出数值型变量的异常点和极端异常点,如下表所示:
利用正态分布的知识点,结合pyplot子模块中的plot函数绘制折线图和散点图,并借助于两条水平参考线识别异常值或极端异常值。
接下来以某公司的支付转化率数据为例,使用正态分布的特性识别数据集中的异常点和极端异常点,该数据呈现的是2017年第三季度每天的支付转化率。我们利用如上介绍的plot函数,识别数据中可能存在的异常点或极端异常点。具体代码如下:
# 读入外部数据 pay_ratio = pd.read_excel(r'C:\Users\Administrator\Desktop\pay_ratio.xlsx') # 绘制单条折线图,并在折线图的基础上添加点图 plt.plot(pay_ratio.date, # x轴数据 pay_ratio.ratio, # y轴数据 linestyle = '-', # 设置折线类型 linewidth = 2, # 设置线条宽度 color = 'steelblue', # 设置折线颜色 marker = 'o', # 往折线图中添加圆点 markersize = 4, # 设置点的大小 markeredgecolor='black', # 设置点的边框色 markerfacecolor='black') # 设置点的填充色 # 显示图形 plt.show() # 添加上下界的水平参考线(便于判断异常点,如下判断极端异常点,只需将2改为3) plt.axhline(y = pay_ratio.ratio.mean() - 2* pay_ratio.ratio.std(), linestyle = '--', color = 'gray') plt.axhline(y = pay_ratio.ratio.mean() + 2* pay_ratio.ratio.std(), linestyle = '--', color = 'gray') # 导入模块,用于日期刻度的修改(因为默认格式下的日期刻度标签并不是很友好) import matplotlib as mpl # 获取图的坐标信息 ax = plt.gca() # 设置日期的显示格式 date_format = mpl.dates.DateFormatter("%m-%d") ax.xaxis.set_major_formatter(date_format) # 设置x轴每个刻度的间隔天数 xlocator = mpl.ticker.MultipleLocator(7) ax.xaxis.set_major_locator(xlocator) # 为了避免x轴刻度标签的紧凑,将刻度标签旋转45度 plt.xticks(rotation=45)
如上图所示,左图中的两条水平线是偏离均值正负2倍标准差的参考线,目测有6个样本点落在参考线之外,可以判定它们属于异常点;而对于右图中偏离均值正负3倍标准差的参考线来说,仅有1个样本点落在参考线之外,即说明该样本点就是2017年第三季度的唯一极端异常点。
同理,也可以借助于下面的代码,查询出异常点所对应的水流量:
# 计算判断异常点和极端异常点的临界值 outlier_ll = pay_ratio.ratio.mean() - 2* pay_ratio.ratio.std() outlier_ul = pay_ratio.ratio.mean() + 2* pay_ratio.ratio.std() extreme_outlier_ll = pay_ratio.ratio.mean() - 3* pay_ratio.ratio.std() extreme_outlier_ul = pay_ratio.ratio.mean() + 3* pay_ratio.ratio.std() # 寻找异常点 pay_ratio.loc[(pay_ratio.ratio > outlier_ul) | (pay_ratio.ratio < outlier_ll), ['date','ratio']] # 寻找极端异常点 pay_ratio.loc[(pay_ratio.ratio > extreme_outlier_ul) | (pay_ratio.ratio < extreme_outlier_ll), ['date','ratio']]
异常点
极端异常点
尽管基于箱线图的分位数法和基于正态分布的参考线法都可以实现异常值和极端异常值的识别,但是在实际应用中,需要有针对性的选择。如果待判断的变量近似服从正态分布,建议选择正态分布的参考线法识别异常点,否则使用分位数法识别异常点。
数据分析咨询请扫描二维码
若不方便扫码,搜微信号:CDAshujufenxi
探索最优回归方程:数据背后的精准预测密码 在数据分析和统计学的广阔领域中,回归分析是揭示变量之间关系的重要工具,而回 ...
2025-07-02CDA 证书:银行招聘中的 “黄金通行证” 在金融科技飞速发展的当下,银行正加速向数字化、智能化转型,海量数据成为 ...
2025-07-02CDA 数据分析师报考条件全解析:开启数据洞察之旅 在当今数字化浪潮席卷全球的时代,数据已成为企业乃至整个社会发展的核心驱 ...
2025-07-01深入解析 SQL 中 CASE 语句条件的执行顺序 在 SQL 编程领域,CASE语句是实现条件逻辑判断、数据转换与分类的重要工 ...
2025-07-01SPSS 中计算三个变量交集的详细指南 在数据分析领域,挖掘变量之间的潜在关系是获取有价值信息的关键步骤。当我们需要探究 ...
2025-07-01CDA 数据分析师:就业前景广阔的新兴职业 在当今数字化时代,数据已成为企业和组织决策的重要依据。数据分析师作为负责收集 ...
2025-06-30探秘卷积层:为何一个卷积层需要两个卷积核 在深度学习的世界里,卷积神经网络(CNN)凭借其强大的特征提取能力 ...
2025-06-30探索 CDA 数据分析师在线课程:开启数据洞察之旅 在数字化浪潮席卷全球的当下,数据已成为企业决策、创新与发展的核心驱 ...
2025-06-303D VLA新范式!CVPR冠军方案BridgeVLA,真机性能提升32% 编辑:LRST 【新智元导读】中科院自动化所提出BridgeVLA模型,通过将 ...
2025-06-30LSTM 为何会产生误差?深入剖析其背后的原因 在深度学习领域,LSTM(Long Short-Term Memory)网络凭借其独特的记忆单元设 ...
2025-06-27LLM进入拖拽时代!只靠Prompt几秒定制大模型,效率飙升12000倍 【新智元导读】最近,来自NUS、UT Austin等机构的研究人员创新 ...
2025-06-27探秘 z-score:数据分析中的标准化利器 在数据的海洋中,面对形态各异、尺度不同的数据,如何找到一个通用的标准来衡量数据 ...
2025-06-26Excel 中为不同柱形设置独立背景(按数据分区)的方法详解 在数据分析与可视化呈现过程中,Excel 柱形图是展示数据的常用工 ...
2025-06-26CDA 数据分析师会被 AI 取代吗? 在当今数字化时代,数据的重要性日益凸显,数据分析师成为了众多企业不可或缺的角色 ...
2025-06-26CDA 数据分析师证书考取全攻略 在数字化浪潮汹涌的当下,数据已成为企业乃至整个社会发展的核心驱动力。数据分析师作 ...
2025-06-25人工智能在数据分析的应用场景 在数字化浪潮席卷全球的当下,数据以前所未有的速度增长,传统的数据分析方法逐渐难以满足海 ...
2025-06-25评估模型预测为正时的准确性 在机器学习与数据科学领域,模型预测的准确性是衡量其性能优劣的核心指标。尤其是当模型预测结 ...
2025-06-25CDA认证:数据时代的职业通行证 当海通证券的交易大厅里闪烁的屏幕实时跳动着市场数据,当苏州银行的数字金融部连夜部署新的风控 ...
2025-06-24金融行业的大数据变革:五大应用案例深度解析 在数字化浪潮中,金融行业正经历着深刻的变革,大数据技术的广泛应用 ...
2025-06-24Power Query 中实现移动加权平均的详细指南 在数据分析和处理中,移动加权平均是一种非常有用的计算方法,它能够根据不同数据 ...
2025-06-24