深度神经网络将requires_grad设为True梯度全为0,step()后还会更新梯度问题的原因

目录

问题

原因

解决方法

方法

结果


问题

偶然发现明明将网络中某一层requires_grad设置为True,在loss.backward()后该层的梯度并不为None,反而全是0,并且optimizer.step()前后参数被更新了。

原因

这是在需要多次使用backward(),step()时会出现的问题,当第一次调用loss.backward(retain_graph=True)时,保留了计算图,因此这个被冻住的层的梯度并不会被清空为None,而是保留了下来,当使用optimizer.zero_grad()后,所有的梯度被置为0,也并不会清除掉。

深度神经网络将requires_grad设为True梯度全为0,step()后还会更新梯度问题的原因_第1张图片

深度神经网络将requires_grad设为True梯度全为0,step()后还会更新梯度问题的原因_第2张图片

虽然是0,但在更新梯度时,该层还是会被更新

深度神经网络将requires_grad设为True梯度全为0,step()后还会更新梯度问题的原因_第3张图片

深度神经网络将requires_grad设为True梯度全为0,step()后还会更新梯度问题的原因_第4张图片

解决方法

方法

解决方案也十分简单,我们的目的是不更新该层梯度,现在虽然没有计算梯度还是更新了,但只要将该层从optimizer要更新的参数的列表中踢出,即可避免该层被更新

self.optimizer.param_groups[0]['params'] = [p for p in self.model.parameters() if p.requires_grad] # 重新给优化器需要更新的参数赋值
    self.optimizer.step()

结果

深度神经网络将requires_grad设为True梯度全为0,step()后还会更新梯度问题的原因_第5张图片

深度神经网络将requires_grad设为True梯度全为0,step()后还会更新梯度问题的原因_第6张图片

你可能感兴趣的:(深度学习,人工智能,深度学习,python)