理论
认识 Optimizer 的方法之前,需要了解一个概念,叫做参数组(param_groups)。在 finetune,某层定制学习率,某层学习率置零操作中,都会设计参数组的概念,因此首先 了解参数组的概念非常有必要。
optimizer 对参数的管理是基于组的概念,可以为每一组参数配置特定的 lr,momentum,weight_decay 等等。
参数组在 optimizer 中表现为一个 list(self.param_groups),其中每个元素是 dict,表示一个参数及其相应配置,在 dict 中包含’params’、‘weight_decay’、‘lr’ 、 'momentum’等字段。
源码
# coding: utf-8
import torch
import torch.optim as optim
w1 = torch.randn(2, 2)
w1.requires_grad = True
w2 = torch.randn(2, 2)
w2.requires_grad = True
w3 = torch.randn(2, 2)
w3.requires_grad = True
# 一个参数组
optimizer_1 = optim.SGD([w1, w3], lr=0.1)
print('len(optimizer.param_groups): ', len(optimizer_1.param_groups))
print(optimizer_1.param_groups, '\n')
# 两个参数组
optimizer_2 = optim.SGD([{'params': w1, 'lr': 0.1},
{'params': w2, 'lr': 0.001}])
print('len(optimizer.param_groups): ', len(optimizer_2.param_groups))
print(optimizer_2.param_groups)
运行
len(optimizer.param_groups): 1
[{'params': [tensor([[0.3673, 0.6950],
[0.4002, 0.1766]], requires_grad=True),
tensor([[0.8128, 0.6266],
[-0.5585,-0.3550]], requires_grad=True)],
'lr': 0.1, 'momentum': 0, 'dampening': 0,
'weight_decay': 0, 'nesterov': False}]
len(optimizer.param_groups): 2
[{'params': [tensor([[0.3673, 0.6950],
[0.4002, 0.1766]], requires_grad=True)],
'lr': 0.1, 'momentum': 0, 'dampening': 0,
'weight_decay': 0, 'nesterov': False},
{'params': [tensor([[ 1.3287, 0.8475],
[ 0.2672, -2.6240]], requires_grad=True)],
'lr': 0.001, 'momentum': 0, 'dampening': 0,
'weight_decay': 0, 'nesterov': False}]