常见的类别不平衡问题解决方法
通常的分类学习方法中都有一个共同的假设,即不同类别的训练样例数目相同。如果不同类别的训练样例数目稍有差别,通常对分类影响不大,但是若差别很大,则会对学习造成影响,测试结果非常差。例如二分类问题中有998个反例,正例有2个,那么学习方法只需返回一个永远将新样本预测为反例的分类器,就能达到99.8%的精度;然而这样的分类器没有价值,我们必须要解决这个问题。
那么,什么是“类别不平衡”?
类别不平衡(class-imbalance)是指分类任务中不同类别的训练样例数目差别很大的情况。
在现实的分类任务中,我们会经常遇到类别不平衡的问题。例如,在银行信用欺诈交易识别中,属于欺诈交易的应该是很少部分,绝大部分交易是正常的,这就是一个正常的类别不平衡问题。一般而已,如果类别不平衡比例超过4:1,那么其分类器会大大地因为数据不平衡性而无法满足分类要求的。因此在构建分类模型之前,需要对分类不平衡性问题进行处理。
解决方法
1、扩大数据集
当遇到类别不均衡问题时,首先应该想到,是否可能再增加数据(一定要有小类样本数据),更多的数据往往战胜更好的算法。因为机器学习是使用现有的数据对整个数据的分布进行估计,因此更多的数据往往能够得到更多的分布信息。即使再增加小类样本数据时,又增加了大类样本数据,也可以使用放弃一部分大类数据(即对大类数据进行欠采样)来解决。
2、欠采样
欠采样(under-sampling):对大类的数据样本进行采样来减少该类数据样本的个数,使其与其他类数目接近,然后再进行学习。欠采样若随机丢弃大类样本,可能会丢失一些重要信息。
欠采样的代表算法是EasyEnsemble:利用集成学习机制,将大类划分为若干个集合供不同的学习器使用。这样对每个学习器来看都进行了欠采样,但在全局来看却不会丢失重要信息。
3、过采样
过采样(over-sampling ):对小类的数据样本进行采样来增加小类的数据样本个数。
过采样的代表算法是SMOTE(原始论文)和ADASYN原始论文
SMOTE:通过对训练集中的小类数据进行插值来产生额外的小类样本数据。产生新的少数类样本,产生的策略是对每个少数类样本a,从它的最近邻中随机选一个样本b,然后在a、b之间的连线上随机选一点作为新合成的少数类样本。
ADASYN:基本思想是根据学习难度的不同,对不同的少数类别的样本使用加权分布,比较容易学习的少数类样本,对于难以学习的少数类的样本,产生更多的综合数据。 因此,ADASYN方法通过两种方式改善了对数据分布的学习:(1)减少类不平衡引入的偏差,(2)将分类决策边界自适应地转移到困难的样本。
SMOTE算法的多个不同语言的实现版本:
1. python:imbalanced-learn
2. Weka:Class SMOTE
总结:采样算法容易实现,运行速度快,且效果也不错。
在欠采样、过采样中的小经验:
3. 考虑对大类下的样本(超过1万、十万甚至更多)进行欠采样,即删除部分样本;
4. 考虑对小类下的样本(不足1为甚至更少)进行过采样,即添加部分样本的副本;
5. 考虑尝试随机采样与非随机采样两种采样方法;
6. 考虑对各类别尝试不同的采样比例,不一定是1:1,有时候1:1反而不好,因为与现实情况相差甚远;
7. 考虑同时使用过采样与欠采样,对二者进行结合;
值得注意的是,使用过采样方法来解决不平衡问题时应适当地应用交叉验证。这是因为过采样会观察到罕见的样本,并根据分布函数应用自举生成新的随机数据,如果在过采样之后应用交叉验证,那么我们所做的就是将我们的模型过拟合于一个特定的人工引导结果。这就是为什么在过度采样数据之前应该始终进行交叉验证,就像实现特征选择一样。只有重复采样数据可以将随机性引入到数据集中,以确保不会出现过拟合问题。
4、使用新评价指标
在一开始的例子中可以看出,准确度这个评价指标在类别不均衡的分类任务中并不适用,甚至进行误导。因此在类别不均衡分类任务中,需要使用更有说服力的评价指标来对分类器进行评价。
1. 混淆矩阵(Confusion Matrix):使用一个表格对分类器所预测的类别与其真实的类别的样本统计,分别为:TP、FN、FP与TN。由此计算精确率(precision)、召回率(recall)、F1值(F1 value)。
2. ROC曲线(ROC Curves)
3. AUC
4. Kappa (Cohen kappa)
5、尝试不同的分类算法
因为不同的算法适用于不同的任务与数据,应该使用不同的算法进行比较。决策树往往在类别不均衡数据上表现不错。它使用基于类变量的划分规则去创建分类树,因此可以强制地将不同类别的样本分开。目前流行的决策树算法有:C4.5、C5.0、CART和Random Forest等。
6、对模型进行惩罚
你可以使用相同的分类算法,但是使用一个不同的角度,比如你的分类任务是识别那些小类,那么可以对分类器的小类样本数据增加权值,降低大类样本的权值(这种方法其实是产生了新的数据分布,即产生了新的数据集,译者注),从而使得分类器将重点集中在小类样本身上。一个具体做法就是,在训练分类器时,若分类器将小类样本分错时额外增加分类器一个小类样本分错代价,这个额外的代价可以使得分类器更加“关心”小类样本。如penalized-SVM和penalized-LDA算法。
如果你锁定一个具体的算法时,并且无法通过使用重采样来解决不均衡性问题而得到较差的分类结果。这样你便可以使用惩罚模型来解决不平衡性问题。但是,设置惩罚矩阵是一个复杂的事,因此你需要根据你的任务尝试不同的惩罚矩阵,并选取一个较好的惩罚矩阵。
7、从一个新的角度理解问题
我们可以从不同于分类的角度去解决数据不均衡性问题,我们可以把那些小类的样本作为异常点(outliers),因此该问题便转化为异常点检测(anomaly detection)与变化趋势检测问题(change detection)。
异常点检测即是对那些罕见事件进行识别。如:银行信用卡诈骗识别,几十万中样本中可能有几百个诈骗用户。这些事件相对于正常情况是很少见的。
变化趋势检测类似于异常点检测,不同在于其通过检测不寻常的变化趋势来识别。如通过观察用户模式或银行交易来检测用户行为的不寻常改变。
将小类样本作为异常点这种思维的转变,可以帮助考虑新的方法去分离或分类样本。这两种方法从不同的角度去思考,让你尝试新的方法去解决问题。
8、创新
仔细对你的问题进行分析与挖掘,是否可以将你的问题划分成多个更小的问题,而这些小问题更容易解决。
1. 将你的大类压缩成小类;
2. 使用One Class分类器(将小类作为异常点)。
比如One Class SVM,通常一类问题出现在需要对训练样本进行一定比例的筛选,或者已知的训练样本都是正样本,而负样本却很少的情况。
这种情况下,往往需要训练一个对于训练样本紧凑的分类边界,就可以通过负样本实验。一个简单的实际例子是:一个工厂对于产品的合格性进行检查时,往往所知道是合格产品的参数,而不合格的产品的参数要么空间比较大,要么知道的很少。这种情况下就可以通过已知的合格产品参数来训练一个一类分类器,得到一个紧凑的分类边界,超出这个边界就认为是不合格产品。
图中左侧原始空间中的红色曲线包围的是合格的产品,转移到特征空间就是红色的超平面。
可以参考知乎什么是一类支持向量机(one class SVM)
3. 使用集成方式,训练多个分类器,然后联合这些分类器进行分类;
4. 对丰富类进行聚类操作,然后进行有监督学习;
首先,我们可以对具有大量样本的丰富类进行聚类操作。假设我们使用的方法是 K-Means聚类算法 。此时,我们可以选择K值为稀有类中的数据样本的个数,并将聚类后的中心点以及相应的聚类中心当做富类样本的代表样例,类标与富类类标一致。经过聚类操作,我们对富类训练样本进行了筛选,接下来我们就可以将相等样本数的K个正负样本进行有监督训练。
参考:
1、http://blog.csdn.net/heyongluoyao8/article/details/49408131
2、http://blog.csdn.net/u013709270/article/details/72967462
2、周志华《机器学习》