在数据科学竞赛中,评价指标的设计是至关重要的,它直接影响着参赛者的行为和竞争结果。然而,有时候某些评价指标可能存在被滥用的风险,这可能会引发一些不公平的竞争行为。
原始评价指标
评价指标是基于 Gini 稳定性度量的。对于每个周数(WEEK_NUM),预测结果会计算一个 Gini 分数。
其中, 表示实际值的累积分布函数, 表示模型预测值的累积分布函数。接下来, 通过对每周的 Gini 分数进行线性回归拟合, 得到一个形如 的线性回归模型。从回归模型中提取出 falling_rate, 计算方式为 。这一指标用于惩罚预测能力下降的模型。
最终的评价指标是:
换句话说, 评价指标由预测结果的 Gini 均值、falling_rate 的最小值乘以 88.0 、以及残差的标准差组成。
指标存在的问题
https://www.kaggle.com/competitions/home-credit-credit-risk-model-stability/discussion/476449
举个例子,考虑一个基于 Gini 稳定性度量的评价指标,其中的一个关键项是 。这个项的存在使得参赛者有可能采取一些不正当手段来提高他们的得分。例如,他们可以故意让模型在测试期间的前半段表现更差,然后在后半段表现更好,以获取更高的评价指标分数。
来探讨一下两种极端情况的可能性:
可以省略平均 Gini 部分; 可以省略关于下降率的部分。如果选择第二种情况,问题就变成了模型被推向短期表现出色但长期不稳定的情况。
Kaggle举办方回应
https://www.kaggle.com/competitions/home-credit-credit-risk-model-stability/discussion/478716
我们将对测试数据集进行更改,以更好地代表生产环境中的客户评分。当模型在生产环境中运行时,它只能看到过去的性能和预测。这部分需要两周的时间来修改,我们将延长比赛的时间。因此,很可能我们将无法重新评分旧的提交。对于这种不便,我们提前向大家致以歉意。
待选评分公式
https://www.kaggle.com/competitions/home-credit-credit-risk-model-stability/discussion/478699
以下是对新稳定性指标的建议,得分本身并不保证我们将在本次比赛中使用该指标。指标的得分只是对我们评价指标的一种近似, 规则:
如果有任何超参数,我将优化它们,并给定边界([-inf,inf]不是有效的区间)。 我不会评分超过三个超参数的指标,这些超参数事先未设置。 指标应该相对容易解释,并且应该与当前稳定性指标有关联,换句话说,我们希望看到一个易于阅读的公式(可解释性),并且它与竞赛数据不直接相关(泛化性)。 得分范围是0-1,得分越高越好。
Current stability metric
def gini_stability(gini_in_time, w_fallingrate=88.0, w_resstd=-0.5):
x = np.arange(len(gini_in_time))
y = gini_in_time
a, b = np.polyfit(x, y, 1)
y_hat = a*x + b
residuals = y - y_hat
res_std = np.std(residuals)
avg_gini = np.mean(gini_in_time)
return avg_gini + w_fallingrate * min(0, a) + w_resstd * res_std
Metric mean log MA by @jacobyjaeger
def metric_jacobyjaeger(gini_in_time, exponent=69, ma_len=4):
x = np.cumsum(gini_in_time, axis=0)
x = np.concatenate([0*x[:1], x], 0)
scores = -np.mean(-np.log(np.maximum((x[ma_len:] - x[:-ma_len])/ma_len, 1e-5))**exponent)
return scores
Metric mean std by @seifachour12
def metric_seifachour12(gini_in_time, alpha=1028, beta=1.97, gamma=0.49):
return (np.abs(beta*(1/beta*np.mean(gini_in_time) + (gamma-np.std(gini_in_time)))-1))**(1/alpha)
Metric mean std by @kononenko
def metric_kononenko(gini_in_time, c=0.90):
return np.mean(gini_in_time) - c*np.std(gini_in_time)
Metric rolling gini max by @davutpolat
def metric_davutpolat(gini_in_time, c=1.82):
max_gini = gini_in_time[0]
cost = 0
for i in range(1, len(gini_in_time)):
max_gini = max(max_gini, gini_in_time[i])
cost += max(0, max_gini - gini_in_time[i])**2
return np.mean(gini_in_time) + c/(len(gini_in_time)-1)*cost
Metric stability with averaging by @at7459
def gini_at7459(gini_in_time, w_fallingrate=88.0, w_resstd=-0.5, f=8):
w_fallingrate /= f + 1
x = np.arange(len(gini_in_time))
y = gini_in_time
a, b = np.polyfit(x, y, 1)
y_hat = a*x + b
residuals = y - y_hat
res_std = np.std(residuals)
avg_gini = np.mean(gini_in_time)
far = a
for s in range(1,f):
start_index = len(x) // f * (s)
end_index = len(x) // f * (s+1)
x_second_fifth = x[start_index:end_index]
y_second_fifth = gini_in_time[start_index:end_index]
x1 = x[start_index:end_index]
y1 = gini_in_time[start_index:end_index]
a1, b1 = np.polyfit(x1, y1, 1)
far += min(0,a1)
return avg_gini + w_fallingrate * (far) + w_resstd * res_std
Metric mean gini
def metric_mean(gini_in_time):
return np.mean(gini_in_time)
想要一起参赛?
可以在下面论坛中一起讨论:http://discussion.coggle.club/t/topic/18
或添加下面微信如竞赛群:






