项目DRN和S3Net都是用的 J. Johnson, A. Alahi, and L. Fei-Fei, 2016《Perceptual losses for real-time style transfer and super-resolution,” in European conference on computer vision》的感知函数
class Vgg19(torch.nn.Module): def __init__(self, requires_grad=False): super(Vgg19, self).__init__() # 加载预训练的模型 # vgg_pretrained_features = models.vgg19(pretrained=True).features # 加载预训练模型 model = models.vgg19(pretrained=True) # 获取中间层特征 vgg_pretrained_features = model.features self.slice1 = torch.nn.Sequential() self.slice2 = torch.nn.Sequential() self.slice3 = torch.nn.Sequential() self.slice4 = torch.nn.Sequential() self.slice5 = torch.nn.Sequential() # 把不同层的特征分别加入不同的模块 for x in range(2): self.slice1.add_module(str(x), vgg_pretrained_features[x]) for x in range(2, 7): self.slice2.add_module(str(x), vgg_pretrained_features[x]) for x in range(7, 12): self.slice3.add_module(str(x), vgg_pretrained_features[x]) for x in range(12, 21): self.slice4.add_module(str(x), vgg_pretrained_features[x]) for x in range(21, 28): self.slice5.add_module(str(x), vgg_pretrained_features[x]) # 设置所有参数都不需要计算梯度 if not requires_grad: for param in self.parameters(): param.requires_grad = False
def forward(self, x, y): x_vgg, y_vgg = self.vgg(x), self.vgg(y) loss = 0 for i in range(len(x_vgg)): loss += self.weights[i] * self.criterion(x_vgg[i], y_vgg[i].detach()) return loss
Charbonnier loss
Charbonnier 损失 ( A general and adaptive robust loss function ),可以看作是鲁棒的 L1 损失函数。
其中 I 和 I^ 分别代表真实图像和来自提出网络的 relit 图像,并且 e 被视为一个微小的常数(例如 10−6 )以实现稳定和鲁棒的收敛。 LC ha 可以还原全局结构并且可以更鲁棒地处理异常值。
e = 10**(-6) loss=torch.mean(torch.sqrt((y_true-y_pre)**2)+e**2) # loss = torch.sqrt((y_true-y_pre)**2) # loss = np.mean(np.sqrt((y_true - y_pre) ** 2) ) return loss
if __name__=='__main__': y_true=torch.tensor([1.0,2.0,3.0]) y_pre=torch.tensor([4.0,5.0,6.0]) res=cha_loss(y_true,y_pre) print(type(res))