У вас есть несколько строк, в которых вы генерируете новые тензоры из конструктора или приведения к другому типу данных. Когда вы делаете это, вы отключаете цепочку операций, через которую вы хотите, чтобы отличалась команда backwards()
.
Это приведение отключает график, потому что приведение не дифференцируемо:
w_r = w_r.type(torch.LongTensor)
Построение тензора из конструктора отключит график:
batchRankLoss = torch.tensor([max(0,alpha - delta(y_i[i], y_j[i])*predy_i[i] - predy_j[i])) for i in range(batchSize)],dtype = torch.float)
Из документов, оборачивая тензор в переменную, установим для grad_fn значение None (также отключение графика):
rankLoss = Variable(rankLossPrev,requires_grad=True)
Если предположить, что ваша функция critereon
является дифференцируемой, то градиенты в настоящее время текут назад только через loss1
и loss2
. Другие ваши градиенты будут перемещаться только до mult
, пока их не остановит вызов type()
. Это согласуется с вашим наблюдением о том, что ваши пользовательские потери не изменяют выход вашей нейронной сети.
Чтобы градиенты могли течь в обратном направлении через ваши пользовательские потери, вам придется кодировать ту же логику, избегая при этом type()
приведений и вычислять rankLoss
без использования списка.