行业知识
【center-loss 中心损失函数】 原理及程序解释(更新中)
文章目录
- 前言
- 问题引出
- open-set问题
- 抛出
- 解决方法
- softmax函数、softmax-loss函数
- 解决
- 代码(center_loss.py)
- 原理
- 程序解释
- 代码运用
- 如何梯度更新
- 首先了解一下基本的梯度下降算法
- 然后
- 补充:外围知识
- ���型
前言
学习一下: 中心损失函数,用于用于深度人脸识别的特征判别方法
论文:https://ydwen.github.io/papers/WenECCV16.pdf
github代码:https://github.com/KaiyangZhou/pytorch-center-loss
参考:史上最全MNIST系列(三)——Centerloss在MNIST上的Pytorch实现(可视化)
问题引出
open-set问题
open-set 问题是一种模式识别中的问题,它指的是当训练集和测试集的类别不完全相同的情况。例如,如果训练集只包含 0 到 9 的数字,而测试集包含了 A 到 Z 的字母,那么就是一个 open-set 问题。这种情况下,分类器不仅要正确识别已知的类别,还要能够拒绝未知的类别,即将它们标记为 unknown 或 outlier。(后来我想这就是一个聚类问题)
open-set 问题与 closed-set 问题相对应,closed-set 问题是指训练集和测试集的类别完全相同的情况。例如,如果训练集和测试集都只包含 0 到 9 的数字,那么就是一个 closed-set 问题。这种情况下,分类器只需要正确识别已知的类别即可。
抛出
当我们要预测的人脸不在训练集中出现过时,我们需要让它不识别出,而不要因为与训练过的人脸相像而误判。
对于常见的图像分类问题,我们常常用softmax loss来求损失。以MNIST数据集为例,如果你的损失采用softmax loss,那么最后各个类别学出来的特征分布大概如下图:(在倒数第二层全连接层输出了一个2维的特征向量)
左图为训练集,右图为测试集,发现结果分类还算不错,但是每一类的界限太过模糊,若从中再加一列,则有可能出现误判。
解决方法
softmax函数、softmax-loss函数
已知softmax的函数为:
在深度学习的分类问题上,意为对应类的概率(符合每个类的概率相加和为1且0 [[0],[4],[2]] labels = labels.unsqueeze(1).expand(batch_size, self.num_classes)# .unsqueeze(1)表示在第1维增加一个维度 .expand()表示扩展维度 mask = labels.eq(classes.expand(batch_size, self.num_classes)) #eq是比较两个tensor是否相等,相等返回1,不相等返回0 # *表示对应元素相乘 dist = distmat * mask.float() # mask.float()将mask转换为float类型 loss = dist.clamp(min=1e-12, max=1e+12).sum() / batch_size # clamp表示将dist中的元素限制在1e-12和1e+12之间 return loss
代码运用
import torchimport torch.nn as nnfrom center_loss import CenterLosscriterion_cent =CenterLoss(10, 2,False) #10个类别,2维torch.manual_seed(0) #设置随机种子x = torch.randn(10, 2) # (32, 2) #32个样本,每个样本2维labels = torch.randint(0, 10, (10,)) # (32,) #32个样本,每个样本一个标签print(x)print(labels)print(criterion_cent(x, labels))
结果:
tensor([[-1.1258, -1.1524], [-0.2506, -0.4339], [ 0.5988, -1.5551], [-0.3414, 1.8530], [ 0.4681, -0.1577], [ 1.4437, 0.2660], [ 1.3894, 1.5863], [ 0.9463, -0.8437], [ 0.9318, 1.2590], [ 2.0050, 0.0537]])tensor([2, 9, 1, 8, 8, 3, 6, 9, 1, 7])tensor(2.9281, grad_fn=)
如何梯度更新
首先了解一下基本的梯度下降算法
【点云、图像】学习中 常见的数学知识及其中的关系与python实战
里的小标题:基于迭代的梯度下降算法,了解到超参数(人为设定的参数):
学习率,w,b等。此算法为拟合出一条线。
伪代码:
1、未达到设定迭代次数
2、迭代次数epoch+1
3、计算损失值
4、计算梯度
5、更新w、b
6、达到迭代次数,结束
然后
看下这里的更新方法
其中,卷积层中初始化的参数 θc,超参数 :λ、α 和学习率 μ ,迭代次数 t 。(λ、α、 μ均可调)
伪代码:
1、当未收敛时:
2、迭代次数t+1
3、计算损失函数 L=Ls+Lc
4、计算反向传播误差(即梯度)
5、更新w
6、更新cj
7、更新θc
8、结束
其中
其中,如果满足条件,则 δ(条件) = 1,如果不满足,则 δ(条件) = 0。
首先:第一个公式不用多说,为中心损失函数对特征xi求偏导,即求梯度。
其次:第二个公式:加入了判断,当条件满足时(即yi=j,即就是在同一类时)Δcj=cj-xi 的小批量的所有和/m+1。相当于累加了误差求平均,以此来作为梯度。
当条件不满足时,即Δcj =0,此时这个分母的+1的作用就体现出来了,分母不能为0嘛。
补充:
第5步后面一个等号成立是因为Lc中没有W项,所以Lc对W的求导为0
第7步也是一样,求梯度,只是写成了求导的链式法则。
补充:外围知识
模型
- ���型