不平衡分类的权重

数据挖掘 机器学习 Python scikit-学习 xgboost 阶级失衡
2022-03-11 06:24:14

我正在处理一个不平衡的分类问题,其中目标变量包含:

np.bincount(y_train)
array([151953,  13273])

151953 零和13273一。

为了解决这个问题,我在定义 DMatrix 时使用了XGBoost's参数:weight

dtrain = xgb.DMatrix(data=x_train, 
                     label=y_train,
                     weight=weights)

对于我一直使用的权重:

bc = np.bincount(y_train)
n_samples = bc.sum()
n_classes = len(bc)
weights = n_samples / (n_classes * bc)
w = weights[y_train.values]

在哪里weightsarray([0.54367469, 6.22413923])并且在最后一行代码中,我只是使用 中的二进制值对其进行索引y_train这似乎是定义权重的正确方法,因为它代表了一个类与另一个类的值的数量之间的实际比率。然而,这似乎有利于少数族裔,这可以通过检查混淆矩阵来看出:

array([[18881, 19195],
       [  657,  2574]])

因此,仅通过尝试不同的权重值,我就意识到在相当接近的权重比下,具体array([1, 7])而言,结果似乎更加合理:

array([[23020, 15056],
       [  837,  2394]])

所以我的问题是:

  • 为什么使用每个类的实际权重会产生较差的指标?
  • 哪种方法是为不平衡问题设置权重的正确方法?
2个回答

根据您选择的准确度指标,您会发现不同的平衡比率给出了指标的最佳值。要了解为什么这是真的,请考虑单独优化精度与单独优化召回率。当没有误报时,精度得到优化(=1.0)。增加负数据的权重会降低正率,从而降低误报权重。所以如果你只是想优化精度,给正数据零权重!您将始终预测负面标签,并且精度将是理想的。同样,对于仅优化召回,将负数据赋予零权重 - 您将始终获得理想的召回值。这些极端情况对于实际应用来说是愚蠢的,但它们确实表明您的“最佳”平衡比率取决于您的指标。

您可能知道,AUC 和 F1 等指标试图在准确率和召回率之间折衷。在缺乏先验信息的情况下,人们通常会尝试在准确率和召回率之间选择“平等平衡”,如 AUC 中所实施的那样。由于 AUC 对数据平衡比较不敏感,所以一般采用 1:1 的数据平衡比较合适。但是,在现实生活中,您可能更关心精确度而不是召回率,反之亦然。因此,您确实需要提前选择指标,具体取决于您要解决的问题。然后保持你的指标固定,改变你的数据平衡,并在真实的测试数据集上查看你训练的模型性能。然后,您可以从您选择的指标和真实世界数据集的角度查看您的模型是否做出了最佳预测。

实例权重文件

XGBoost 支持为每个实例提供一个权重来区分实例的重要性。例如,如果我们为示例中的“train.txt”文件提供一个实例权重文件,如下所示:

火车.txt.重量

1

0.5

0.5

1

0.5

这意味着 XGBoost 会更加强调第一个和第四个实例,也就是训练时的正实例。配置与配置组信息类似。如果实例文件名为“xxx”,XGBoost 会检查同目录下是否有名为“xxx.weight”的文件,如果有,则在训练模型时使用权重。

  1. 重要并不总是等同于平衡。
  2. 甚至不要设置权重,只要确保问题是平衡的,这方面有很多资源。