目录
19-ICCV-SoftTriple Loss:Deep Metric Learning Without Triplet Sampling


1)SoftMax loss is equivalent to a smoothed triplet loss where each class has a single center.
现实中一个类不只有一个中心,例如鸟有很多姿势(从细粒度角度解释)。扩展SoftMax loss,每个类有多中心。
2)learn the embeddings without the sampling phase by mildly increasing the size of the last fully connected layer.不需要采样。

![]()
最小化有平滑项 λ的normalized SoftMax loss=最大化平滑的triplet loss
这接下来都是证明推导了些啥??
![]()
每个类c有k个中心。
对于样本xi选择相似度最大的中心。
![]()
样本xi与所属类yi的距离比其他类j小。

Inspired by the SoftMax loss, improve the robustness by smoothing the max operator.
原本是直接选最大值。
现在是对所有值加权求和,为保证和最大,原本较大的值对应的权值q一定也大。


类中心越多,类内方差越小;中心数=样本数时,类内方差为0。
一个中心到其他中心的距离
K个中心间的L2距离求和
共N个样本,最小化中心间的距离,为0时即合并。

- class SoftTriple(nn.Module):
- def __init__(self, la, gamma, tau, margin, dim, cN, K):
- super(SoftTriple, self).__init__()
- self.la = la
- self.gamma = 1./gamma
- self.tau = tau
- self.margin = margin
- self.cN = cN # 有cN个类
- self.K = K # 每个类K个中心
- self.fc = Parameter(torch.Tensor(dim, cN*K))
- self.weight = torch.zeros(cN*K, cN*K, dtype=torch.bool).cuda()
- for i in range(0, cN):
- for j in range(0, K):
- self.weight[i*K+j, i*K+j+1:(i+1)*K] = 1
- init.kaiming_uniform_(self.fc, a=math.sqrt(5))
- return
-
- def forward(self, input, target):
- centers = F.normalize(self.fc, p=2, dim=0)
- simInd = input.matmul(centers)
- simStruc = simInd.reshape(-1, self.cN, self.K)
- prob = F.softmax(simStruc*self.gamma, dim=2)
- simClass = torch.sum(prob*simStruc, dim=2)
- marginM = torch.zeros(simClass.shape).cuda()
- marginM[torch.arange(0, marginM.shape[0]), target] = self.margin
- lossClassify = F.cross_entropy(self.la*(simClass-marginM), target)
- if self.tau > 0 and self.K > 1:
- simCenter = centers.t().matmul(centers)
- reg = torch.sum(torch.sqrt(2.0+1e-5-2.*simCenter[self.weight]))/(self.cN*self.K*(self.K-1.))
- return lossClassify+self.tau*reg
- else:
- return lossClassify
代码里Sij也减去marginM了?
代码:GitHub - idstcv/SoftTriple: PyTorch Implementation for SoftTriple Loss