使用不平衡数据进行过度训练

Posted

技术标签:

【中文标题】使用不平衡数据进行过度训练【英文标题】:Overtraining with imbalanced data 【发布时间】:2017-11-09 01:58:45 【问题描述】:

我正在尝试对一些不平衡的数据(约 20:1 的比率)执行二元分类,并获得了几乎完美的交叉验证准确度,但对于未用于训练/测试的数据的预测率却很糟糕。有几千个负例和几百个正例。该数据已经过归一化,并使用 SMOTE 来平衡类分布。

使用 RandomForests 分类器,KFold 交叉验证几乎是完美的,但召回/准确率值介于 0.1-0.3 之间。我尝试了不同的平衡方法,PCA(大约有 80 个原始特征)、多个分类器、CV Grid 优化,甚至在 8 倍训练后组合树,但这些都没有显着改善结果。

与新数据相比,我有点惊讶训练的效果。这可能是因为过度训练吗?我希望树木的结合有助于缓解这种情况,但事实并非如此。 这些数据可能难以使用可用功能进行分类,但有什么明显的我遗漏的吗?

【问题讨论】:

是的,绝对有可能。或者,新数据可能与使用的训练/交叉验证数据有很大不同。顺便说一句,由于这个问题不是关于编程,而是更多关于方法或技术,这不适合 ***.com。在stats.stackexchange.com 上尝试这个问题以及有关代码、数据和您采取的精确步骤的更多详细信息。 【参考方案1】:

解决方案其实很简单。对于这种不平衡的分类,您需要加权您的分类,以便您的模型学会如何平等地分类真假,而不必丢弃大量数据!

试试这个简单的例子:

def calculate_class_weights(train_classifications):

    one_count = 0
    zero_count = 0
    one_weight = 0

    for i in train_classifications:
        if i == 1:
            one_count += 1.0
        if i == 0:
            zero_count += 1.0

    if one_count > zero_count:
        one_weight = one_count / zero_count

    if one_count < zero_count:
        one_weight = zero_count / one_count

    return one_weight

这将给出正分类与负分类相比的相对“权重”。然后你可以这样调用你的模型:

classifier = svm.SVC(probability=True, class_weight=1: one_weight)
classifier.fit(training_set, train_classifiers)

所以这里负数的权重是1,正数的权重是之前计算的。例如,如果正数是负数的两倍,则可能是 0.5。

祝你好运!

【讨论】:

以上是关于使用不平衡数据进行过度训练的主要内容,如果未能解决你的问题,请参考以下文章

如何在不过度采样的情况下平衡数据集

训练测试拆分后不平衡数据的欠采样

使用多层感知器对不平衡数据集进行分类

使用不平衡学习进行过采样后的训练形状输出

处理不平衡数据的策略

如何在管道中重新采样文本(不平衡组)?