在正常的行人重識別深度學習的模型中,都是先將行人圖片經過backbonne網絡,提取特徵,然後再將特徵和Linear層進行了鏈接,然後根據輸出的分類概率,來反饋,對網絡進行優化。我就在想,可不可以不經過最後的分類層,而是直接在特徵的層面進行優化。所以我寫了一個損失函數:
import torch
import torch.nn as nn
class Features_Loss(nn.Module):
def __init__(self):
super(Features_Loss,self).__init__()
def forward(self, features, batch_size, person_num):
loss_all = 0
loss_temp = 0
for id_index in range( batch_size // person_num ):
features_temp_list = features[id_index*person_num:(id_index+1)*person_num+1]
loss_temp = 0
distance = torch.mm(features_temp_list,features_temp_list.t())
distance = 1 -distance
for i in range(person_num):
for j in range( i + 1, person_num ):
loss_temp = loss_temp + distance[i][j]
loss_temp = loss_temp / ( person_num * (person_num-1)/2 )
loss_all = loss_all + loss_temp
loss_all = loss_all / ( batch_size // person_num )
return loss_all
送入這個損失函數的都是經過了標準化的特徵向量,這個函數讓相同label的行人圖片的特徵在餘弦距離這個層面上拉近。
在數據的準備階段,我讓每個batch中包含K個ID的行人,每個ID下面存在N張圖片,就像是triplet loss那樣對數據的mini batch進行採樣。
訓練的時候,我首相將epoch設置爲1,產生了epoch1.pth爲訓練的結果,然後又設置爲60進行訓練,這次的訓練結果爲epoch60.pth 。
我們的這個訓練過程的代碼,以及訓練好的模型,都上傳到了github上,地址爲:https://github.com/t20134297/reid_with_features_loss_only
首先運行 python3 train.py來訓練模型,然後運行python3 test.py就可以測試了,這個簡單的模型獲得rank1在60%左右。