【实操】涨点神器你还不会,快点进来学习Label Smooth

简介: 【实操】涨点神器你还不会,快点进来学习Label Smooth

前言

  相信大家在进来后主要目的是学习如何涨点,那么在本文中我们将着重于实操,捎带讲解一些Label Smooth原理。

  Label Smooth的提出是在yolov4中首次被提出,在训练神经网络的过程中“过拟合”现象是我们经常会碰到的麻烦, 而解决“过拟合”现象有效途径之一就是label smoothing,即:Label Smooth可以看作是一种防止过拟合的正则化方法。

原理

  Label Smooth的原理主要是在One-Hot标签中加入噪声,减少训练时GroundTruth在计算损失函数的权重,来达到防止过拟合的作用,增强模型的泛化能力;

  假设:我们一个5分类的任务,我们在没有经过label smoothing时的数据得到的数据如下

lua

复制代码

out = tensor([[ 0,  0,  0,  0,  1]], device='cuda:0', grad_fn=<AddmmBackward>)

  我们需要使目标out从ont-hot 标签转变为soft label,也即是原来的1的位置上的数变为1 - a ,其它为0的位置上的数转变为a / (K - 1),这里的a通常是取0.1,K为数据类别数。

  那么经过 Label Smooth 后的输出为:

lua

复制代码

LabelSmoothOut = tensor([[ 0.025,  0.025,  0.025,  0.025,  0.9]], device='cuda:0', grad_fn=<AddmmBackward>)

  上述的操作已经被大佬从概率上证实确实是可以进行优化结果,感兴趣的话大家可以自信搜索(arxiv.org/pdf/1906.02…)

实操 Label Smooth

  下文中就进入到实操环节,例举4个关于Label Smooth的操作。

交叉熵损失与概率

参考:Devin Yang示例

python

复制代码

import torch
import torch.nn as nn
from torch.autograd import Variable
class LabelSmoothingLoss(nn.Module):
    def __init__(self, classes, smoothing=0.0, dim=-1, weight=None):
        """if smoothing == 0, it's one-hot method
           if 0 < smoothing < 1, it's smooth method
        """
        super(LabelSmoothingLoss, self).__init__()
        self.confidence = 1.0 - smoothing
        self.smoothing = smoothing
        self.weight = weight
        self.cls = classes
        self.dim = dim
    def forward(self, pred, target):
        assert 0 <= self.smoothing < 1
        pred = pred.log_softmax(dim=self.dim)
        if self.weight is not None:
            pred = pred * self.weight.unsqueeze(0)
        with torch.no_grad():
            true_dist = torch.zeros_like(pred)
            true_dist.fill_(self.smoothing / (self.cls - 1))
            true_dist.scatter_(1, target.data.unsqueeze(1), self.confidence)
        return torch.mean(torch.sum(-true_dist * pred, dim=self.dim))
if __name__ == "__main__":
    crit = LabelSmoothingLoss(classes=5, smoothing=0.1)
    predict = torch.FloatTensor([[1, 0, 0, 0, 0],
                                 [0, 1, 0, 0, 0],
                                 [0, 0, 1, 0, 0]])
    v = crit(Variable(predict), Variable(torch.LongTensor([2, 1, 0])))
    print(v)

Shital Shah示例

python

复制代码

import torch
import torch.nn.functional as F
from torch.autograd import Variable
from torch.nn.modules.loss import _WeightedLoss
class SmoothCrossEntropyLoss(_WeightedLoss):
    def __init__(self, weight=None, reduction='mean', smoothing=0.0):
        super().__init__(weight=weight, reduction=reduction)
        self.smoothing = smoothing
        self.weight = weight
        self.reduction = reduction
    def k_one_hot(self, targets: torch.Tensor, n_classes: int, smoothing=0.0):
        with torch.no_grad():
            targets = torch.empty(size=(targets.size(0), n_classes),
                                  device=targets.device) \
                .fill_(smoothing / (n_classes - 1)) \
                .scatter_(1, targets.data.unsqueeze(1), 1. - smoothing)
        return targets
    def reduce_loss(self, loss):
        return loss.mean() if self.reduction == 'mean' else loss.sum() \
            if self.reduction == 'sum' else loss
    def forward(self, inputs, targets):
        assert 0 <= self.smoothing < 1
        targets = self.k_one_hot(targets, inputs.size(-1), self.smoothing)
        log_preds = F.log_softmax(inputs, -1)
        if self.weight is not None:
            log_preds = log_preds * self.weight.unsqueeze(0)
        return self.reduce_loss(-(targets * log_preds).sum(dim=-1))
if __name__ == "__main__":
    crit = SmoothCrossEntropyLoss(smoothing=0.5)
    tensorData = [[0, 0.2, 0.7, 0.1, 0, 0.15], [0, 0.9, 0.2, 0.2, 1, 0.15], [1, 0.2, 0.7, 0.9, 1, 0.15]]
    predict = torch.FloatTensor(tensorData)
    v = crit(Variable(predict),
             Variable(torch.LongTensor([2, 1, 0])))
    print(v)

标签平滑交叉熵损失

相较于上述两割我们稍微最小化编码写法以使其更简洁:

Datasaurus示例

python

复制代码

import torch
import torch.nn.functional as F
from torch.autograd import Variable
class LabelSmoothingLoss(torch.nn.Module):
    def __init__(self, smoothing: float = 0.1,
                 reduction="mean", weight=None):
        super(LabelSmoothingLoss, self).__init__()
        self.smoothing   = smoothing
        self.reduction = reduction
        self.weight    = weight
    def reduce_loss(self, loss):
        return loss.mean() if self.reduction == 'mean' else loss.sum() \
         if self.reduction == 'sum' else loss
    def linear_combination(self, x, y):
        return self.smoothing * x + (1 - self.smoothing) * y
    def forward(self, preds, target):
        assert 0 <= self.smoothing < 1
        if self.weight is not None:
            self.weight = self.weight.to(preds.device)
        n = preds.size(-1)
        log_preds = F.log_softmax(preds, dim=-1)
        loss = self.reduce_loss(-log_preds.sum(dim=-1))
        nll = F.nll_loss(
            log_preds, target, reduction=self.reduction, weight=self.weight
        )
        return self.linear_combination(loss / n, nll)
if __name__=="__main__":
    crit = LabelSmoothingLoss(smoothing=0.3, reduction="mean")
    predict = torch.FloatTensor([[0, 0.2, 0.7, 0.1, 0],
                                 [0, 0.9, 0.2, 0.2, 1],
                                 [1, 0.2, 0.7, 0.9, 1]])
    v = crit(Variable(predict),
             Variable(torch.LongTensor([2, 1, 0])))
    print(v)

NVIDIA/DeepLearning示例

python

复制代码

import torch
import torch.nn as nn
import torch.nn.functional as F
from torch.autograd import Variable
class LabelSmoothing(nn.Module):
    """NLL loss with label smoothing.
    """
    def __init__(self, smoothing=0.0):
        """Constructor for the LabelSmoothing module.
        :param smoothing: label smoothing factor
        """
        super(LabelSmoothing, self).__init__()
        self.confidence = 1.0 - smoothing
        self.smoothing = smoothing
    def forward(self, x, target):
        logprobs = torch.nn.functional.log_softmax(x, dim=-1)
        nll_loss = -logprobs.gather(dim=-1, index=target.unsqueeze(1))
        nll_loss = nll_loss.squeeze(1)
        smooth_loss = -logprobs.mean(dim=-1)
        loss = self.confidence * nll_loss + self.smoothing * smooth_loss
        return loss.mean()
if __name__ == "__main__":
    crit = LabelSmoothing(smoothing=0.3)
    predict = torch.FloatTensor([[0, 0.2, 0.7, 0.1, 0],
                                 [0, 0.9, 0.2, 0.2, 1],
                                 [1, 0.2, 0.7, 0.9, 1]])
    v = crit(Variable(predict),
             Variable(torch.LongTensor([2, 1, 0])))
    print(v)

参考:

  1. github.com/pytorch/pyt…
  2. stackoverflow.com/a/59264908/…
  3. www.kaggle.com/c/siim-isic…
  4. github.com/NVIDIA/Deep…
  5. stackoverflow.com/questions/5….


相关文章
|
机器学习/深度学习 人工智能 自然语言处理
视觉 注意力机制——通道注意力、空间注意力、自注意力
本文介绍注意力机制的概念和基本原理,并站在计算机视觉CV角度,进一步介绍通道注意力、空间注意力、混合注意力、自注意力等。
14267 58
|
Windows
mathtype7产品激活密钥最新
MathType是强大的数学公式编辑器,MathType公式编辑器可以说是专门为理科生准备的软件,它可以帮助用户快速的在各种文档中插入符号和公式,不论是简单的公式和符号,还是复杂的都可以非常轻松的输入,并且在与office文档结合使用时,表现的非常完美,是非常好的一款软件,与常见的文字处理软件和演示程序配合使用,能够在各种文档中加入复杂的数学公式和符号,可用在编辑数学试卷、书籍、报刊、论文、幻灯演示等方面,是编辑数学资料的得力工具。
54244 0
|
计算机视觉
YOLOv5改进 | 检测头篇 | 增加辅助检测头利用AFPN改进Head(附详细修改教程)
YOLOv5改进 | 检测头篇 | 增加辅助检测头利用AFPN改进Head(附详细修改教程)
1048 0
|
PyTorch 算法框架/工具
Pytorch学习笔记(五):nn.AdaptiveAvgPool2d()函数详解
PyTorch中的`nn.AdaptiveAvgPool2d()`函数用于实现自适应平均池化,能够将输入特征图调整到指定的输出尺寸,而不需要手动计算池化核大小和步长。
1310 1
Pytorch学习笔记(五):nn.AdaptiveAvgPool2d()函数详解
|
机器学习/深度学习 人工智能 JSON
知识蒸馏方法探究:Google Distilling Step-by-Step 论文深度分析
大型语言模型(LLM)的发展迅速,从简单对话系统进化到能执行复杂任务的先进模型。然而,这些模型的规模和计算需求呈指数级增长,给学术界和工业界带来了挑战。为解决这一问题,知识蒸馏技术应运而生,旨在将大型模型的知识转移给更小、更易管理的学生模型。Google Research 提出的“Distilling Step-by-Step”方法不仅减小了模型规模,还通过提取推理过程使学生模型在某些任务上超越教师模型。该方法通过多任务学习框架,训练学生模型同时预测标签和生成推理过程,从而实现更高效、更智能的小型化模型。这为资源有限的研究者和开发者提供了新的解决方案,推动了AI技术的普及与应用。
663 19
知识蒸馏方法探究:Google Distilling Step-by-Step 论文深度分析
|
并行计算 PyTorch 算法框架/工具
yolov5训练太慢的解决方案
这篇文章讨论了YOLOv5训练速度慢的问题,并提供了解决方案,主要是由于没有安装CUDA和支持GPU的PyTorch版本,导致只有CPU在工作。文章建议安装CUDA和正确配置支持GPU的PyTorch以加速训练过程。
1280 1
yolov5训练太慢的解决方案
|
机器学习/深度学习 算法 前端开发
集成学习(Ensemble Learning)是一种机器学习技术,它通过将多个学习器(或称为“基学习器”、“弱学习器”)的预测结果结合起来,以提高整体预测性能。
集成学习(Ensemble Learning)是一种机器学习技术,它通过将多个学习器(或称为“基学习器”、“弱学习器”)的预测结果结合起来,以提高整体预测性能。
|
机器学习/深度学习 存储 算法
Pandas中的get_dummies()函数实战应用详解
Pandas中的get_dummies()函数实战应用详解
1280 1
inkscape
inkscape使用教程
671 1
|
机器学习/深度学习 自动驾驶 计算机视觉
YOLOv5改进 | Neck篇 | Slim-Neck替换特征融合层实现超级涨点 (又轻量又超级涨点)
YOLOv5改进 | Neck篇 | Slim-Neck替换特征融合层实现超级涨点 (又轻量又超级涨点)
1358 0
YOLOv5改进 | Neck篇 | Slim-Neck替换特征融合层实现超级涨点 (又轻量又超级涨点)

热门文章

最新文章