XGBoost 增加了改变评估函数时的误差

数据挖掘 xgboost 评估
2022-03-07 05:38:04

我已将 XGBoost 的 eval 函数更改为 rmsle,并且优化在迭代 [2] 后增加了误差,而不是减少了误差。如果我更改为默认的 eval 函数 RMSE,则不会发生这种情况。

这是使用的 RMSLE 代码:

def evalerror(preds, dtrain): # this is compatible with DMatrix
    labels = dtrain.get_label()
    assert len(preds) == len(labels)
    labels = labels.tolist()
    preds = preds.tolist()
    terms_to_sum = [(math.log(labels[i] + 1) - math.log(max(0,preds[i]) + 1)) ** 2.0 for i,pred in enumerate(labels)]
    return 'error', (sum(terms_to_sum) * (1.0/len(preds))) ** 0.5

这是使用的 XGBoost 的参数:

param = {'bst:max_depth':1, 'bst:eta':0.025, 'silent':False, 'objective':'reg:linear','eval_metric':'rmse' }
bst = xgb.train( param, d_train, num_rounds,early_stopping_rounds=20, evals=eval_list, verbose_eval=True, feval=evalerror)

这是评估:

[0] eval-error:0.836219 train-error:0.835095
Multiple eval metrics have been passed: 'train-error' will be used for early stopping.

Will train until train-error hasn't improved in 20 rounds.
[1] eval-error:0.809301 train-error:0.806747
[2] eval-error:0.792647 train-error:0.78908
[3] eval-error:0.803355 train-error:0.798805
[4] eval-error:0.803261 train-error:0.79835
[5] eval-error:0.809352 train-error:0.804283
[6] eval-error:0.810453 train-error:0.805126
[7] eval-error:0.811059 train-error:0.805646
[8] eval-error:0.815261 train-error:0.809722
[9] eval-error:0.820237 train-error:0.814521
[10]    eval-error:0.823378 train-error:0.817408
[11]    eval-error:0.824981 train-error:0.81868
[12]    eval-error:0.826607 train-error:0.820176
[13]    eval-error:0.827813 train-error:0.821358
[14]    eval-error:0.827625 train-error:0.821007
[15]    eval-error:0.823347 train-error:0.816547
[16]    eval-error:0.824362 train-error:0.81752
[17]    eval-error:0.82529  train-error:0.818321
[18]    eval-error:0.824621 train-error:0.817463
[19]    eval-error:0.824103 train-error:0.816766
[20]    eval-error:0.814759 train-error:0.807234
[21]    eval-error:0.807961 train-error:0.800186
[22]    eval-error:0.808398 train-error:0.800246
Stopping. Best iteration:
[2] eval-error:0.792647 train-error:0.78908

可能是我需要将我的目标函数调整为这个评估指标?

2个回答

如果您的目标是最小化 RMSLE,更简单的方法是将标签直接转换为对数刻度并reg:linear用作目标(这是默认值)和rmse评估指标。这样 XGBoost 将最小化 RMSLE 直接。您可以通过设置:

dtrain = DMatrix(X_train, label=np.log1p(y_train))

其中np.log1p(x)等于np.log(x+1)

当您想在原始空间中进行预测时,您需要计算 的逆变换np.log1p,即np.expm1

predictions = np.expm1(bst.predict(dtest))

如果您只是对通过 XGBoost 的训练来监控 RMSLE 感兴趣,这实际上是在最小化 RMSE,那么您应该会看到 RMSLE 的行为有点奇怪,因为它不是您要最小化的。

在使用 RMSLE 时,您应该注意指标对低于预测值的惩罚比对过度预测值的惩罚更多,从而将模型推向高偏差。这可能会改变模型的权重,从而在第二次迭代后增加误差。 你可以去以下链接