今天学习了关于样本类别分布不均衡的处理的一些知识,在此和大家一起分享一下。
什么是样本类别分布不均衡?
举例说明,在一组样本中不同类别的样本量差异非常大,比如拥有1000条数据样本的数据集中,有一类样本的分类只占有10条,此时属于严重的数据样本分布不均衡。
样本类别分布不均衡导致的危害?
样本类别不均衡将导致样本量少的分类所包含的特征过少,并很难从中提取规律;即使得到分类模型,也容易产生过度依赖与有限的数据样本而导致过拟合问题,当模型应用到新的数据上时,模型的准确性会很差。
解决方法:
1.通过过抽样和欠抽样解决样本不均衡
(1)过抽样(over-sampling):通过增加分类中少数类样本的数量来实现样本均衡,比较好的方法有SMOTE算法。
SMOTE算法:简单来说smote算法的思想是合成新的少数类样本,合成的策略是对每个少数类样本a,从它的最近邻中随机选一个样本b,然后在a、b之间的连线上随机选一点作为新合成的少数类样本。具体的过程大家可以自行google。
附上代码示例:(首先展示示例数据,本篇文章都用此数据)
import pandas as pd from imblearn.over_sampling import SMOTE #过度抽样处理库SMOTE df=pd.read_table('data2.txt',sep=' ',names=['col1','col2','col3','col4','col5','label']) x=df.iloc[:,:-1] y=df.iloc[:,-1] groupby_data_orginal=df.groupby('label').count() #根据标签label分类汇总
扫描二维码关注公众号,回复:
1154945 查看本文章
用groupby可以看到该数据label=0的有942个样本,label=1的只有58个,存在严重的不均衡现象,在这里我们用SMOTE算法来解决一下。
model_smote=SMOTE() #建立smote模型对象 x_smote_resampled,y_smote_resampled=model_smote.fit_sample(x,y) x_smote_resampled=pd.DataFrame(x_smote_resampled,columns=['col1','col2','col3','col4','col5']) y_smote_resampled=pd.DataFrame(y_smote_resampled,columns=['label']) smote_resampled=pd.concat([x_smote_resampled,y_smote_resampled],axis=1) groupby_data_smote=smote_resampled.groupby('label').count()
可以看到通过smote算法将原本只有58个数据的样本补齐成了942。
(2)欠抽样(under-sampling):通过减少分类中多数类样本的数量来实现样本均衡
from imblearn.under_sampling import RandomUnderSampler model_RandomUnderSampler=RandomUnderSampler() #建立RandomUnderSample模型对象 x_RandomUnderSample_resampled,y_RandomUnderSample_resampled=model_RandomUnderSampler.fit_sample(x,y) #输入数据并进行欠抽样处理 x_RandomUnderSample_resampled=pd.DataFrame(x_RandomUnderSample_resampled,columns=['col1','col2','col3','col4','col5']) y_RandomUnderSample_resampled=pd.DataFrame(y_RandomUnderSample_resampled,columns=['label']) RandomUnderSampler_resampled=pd.concat([x_RandomUnderSample_resampled,y_RandomUnderSample_resampled],axis=1) groupby_data_RandomUnderSampler=RandomUnderSampler_resampled.groupby('label').count()
根据数据可看到通过随机欠抽样方法,将原本942条数据的label0删减成为58条。
2.通过正负样本的惩罚权重解决样本不均衡
算法思想:对于分类中不同样本数量的类别分别赋予不同的权重,一般是小样本量类别权重高,大样本量类别权重低。
这里以SVM为例:
from sklearn.svm import SVC model_svm=SVC(class_weight='balanced') model_svm.fit(x,y)这里的class_weight选项用其默认方法‘balanced’,即SVM会将权重设置为与不同类别样本数量呈反比的权重来进行自动均衡处理。