python - 我如何处理pytorch中的多重损失?

标签 python pytorch

enter image description here

例如,我想使用一些辅助损失来提升我的模型性能。
哪种类型的代码可以在pytorch中实现?

#one
loss1.backward()
loss2.backward()
loss3.backward()
optimizer.step()
#two
loss1.backward()
optimizer.step() 
loss2.backward()
optimizer.step() 
loss3.backward()
optimizer.step()   
#three
loss = loss1+loss2+loss3
loss.backward()
optimizer.step()

感谢您的回答!

最佳答案

第一次和第三次尝试完全相同且正确,而第二种方法完全错误。

在 Pytorch 中,低层梯度不会被随后的 backward() 调用“覆盖”,而是被累积或求和。这使得第一种和第三种方法相同,但如果您的 GPU/RAM 内存较低(批处理大小为 1024,一次 backward() + step() 调用与具有8 个大小为 128 的批处理和 8 个 backward() 调用,最后有一个 step() 调用。

为了说明这个想法,这里有一个简单的例子。我们想让张量 x 同时接近 40,50 和 60:

x = torch.tensor([1.0],requires_grad=True)
loss1 = criterion(40,x)
loss2 = criterion(50,x)
loss3 = criterion(60,x)

现在是第一种方法:(我们使用 tensor.grad 来获取张量 x 的当前梯度)

loss1.backward()
loss2.backward()
loss3.backward()

print(x.grad)

此输出:tensor([-294.])(编辑:将 retain_graph=True 放在前两个 backward 调用中以获得更复杂的计算图)

第三种方法:

loss = loss1+loss2+loss3
loss.backward()
print(x.grad)

再次输出:tensor([-294.])

第二种方法不同,因为我们在调用 step() 方法后不调用 opt.zero_grad。这意味着在所有 3 个 step 调用中使用第一个 backward 调用的梯度。例如,如果 3 次损失为相同的权重提供梯度 5,1,4,而不是 10 (=5+1+4),现在您的权重将为 5*3+1 *2+4*1=21 作为梯度。

进一步阅读:Link 1 , Link 2

关于python - 我如何处理pytorch中的多重损失?,我们在Stack Overflow上找到一个类似的问题: https://stackoverflow.com/questions/53994625/

相关文章:

Python:将脚本从过程风格转换为 OOP 风格

python - 情节破折号下载字节流

python - 如何通过 subprocess.Popen 接收 pickle

python - 如何选择只有正值的列?

python - AutoTokenizer.from_pretrained 无法加载本地保存的预训练标记器 (PyTorch)

nlp - 如何使用 Pytorch 计算语言模型的困惑度

python - 如何从 Azure blob 数据存储获取 Python pathlib 路径?

python - Beautifulsoup:获取一系列 div

python - 为什么 torch.nn.Sigmoid 是一个类而不是一个方法?

python - pytorch 中的 Keras 学习率衰减