|
label smoothing标签平滑的工作原理
防止过拟合
对于ground truth为one-hot的情况,使用模型去拟合这样的函数具有两个问题:首先,无法保证模型的泛化能力,容易导致过拟合; 其次,全概率和零概率将鼓励所属类别和非所属类别之间的差距会被尽可能拉大,因为模型太过相信自己的预测了。
为了解决这一问题,使得模型没有那么肯定,提出了label smoothing。
clf_loss = slim.losses.softmax_cross_entropy(logits, onehot_labels=gt_liveness_oh, label_smoothing=0.1)
- import os
- import tensorflow as tf
- import numpy as np
- # 假设有一批数据在神经网络最后一层的输出值和他们的真实标签
- y_predict = np.array([[4.0, 5.0, 10.0], [1.0, 5.0, 4.0], [1.0, 15.0, 4.0]])
- y_true_oh = np.array([[0, 0, 1], [0, 1, 0], [0, 1, 0]])
- # 直接计算softmax交叉熵损失:
- res = tf.losses.softmax_cross_entropy(logits=y_predict, onehot_labels=y_true_oh, label_smoothing=0)
- res_smooth = tf.losses.softmax_cross_entropy(logits=y_predict, onehot_labels=y_true_oh, label_smoothing=0.01)
- res_val, res_smooth_val = tf.Session().run([res, res_smooth])
- print("没有进行标签平滑的loss={}, 进行了标签平滑的loss={}".format(res_val, res_smooth_val))
- # 标签平滑的原理是对真实标签做了改变
- # new_onehot_labels = onehot_labels * (1 - label_smoothing) + label_smoothing / num_classes
- new_onehot_labels = y_true_oh * (1 - 0.01) + 0.01 / 3
- print("原始实际值:", y_true_oh)
- print("平滑后的实际值:", new_onehot_labels)
- # 然后使用平滑标签计算softmax交叉熵就能得到最终的结果了,我们也可以验证一下:
- res_smooth2 = tf.losses.softmax_cross_entropy(onehot_labels=new_onehot_labels, logits=y_predict, label_smoothing=0)
- print("进行了标签平滑的loss={}".format(tf.Session().run(res_smooth2)))
复制代码
|
|