博客
关于我
强烈建议你试试无所不能的chatGPT,快点击我
逐层指定学习率
阅读量:5235 次
发布时间:2019-06-14

本文共 4140 字,大约阅读时间需要 13 分钟。

为不同的层指定相应的学习率可能会有些用处,印象中,这个在caffe里面是在定义网络时指定的,用mxnet后一直没用到过。这放一些字符,以备查。

接口

思路来自于。

但在optimizer.py中,相应的接口为set_lr_mult(self, args_lr_mult)
其思路是:在 mod._optimizer 内部定义一个字典以记录每个参数的学习率乘子。
值得注意的是,从程序上来看,这个接口并不是按照层为单位进行学习率设定,而是对具体的参数进行设置(比如:conv1_weight)。


Nov 5, 2017

试验的几次都把怀疑目标指向了这个地方,今早测试了下。问题出在set_lr_mult传入的dictionary上,其内容应当包括所有要调整的参数,不能使用单个多次指定的方式


测试

# updated on Nov 5, 2017import mxnet as mxM,N=3,3num_filter=1kernel=mx.nd.array([ [1,2,3],[1,2,3],[1,2,3] ])d=mx.sym.Variable('data')conv1=mx.sym.Convolution(data=d,kernel=(3,3),num_filter=num_filter,no_bias=False,name='conv1')loss=mx.sym.MakeLoss(data=conv1)bch_kernel=kernel.reshape((1,1,M,N))arg_params={'conv1_weight': bch_kernel}mod=mx.mod.Module(symbol=loss,data_names=('data',),label_names=None)mod.bind(data_shapes=[ ('data',[1,1,M,N]),])mod.init_params()   mod.init_optimizer()  ###################################################################   Solution I  ############################################################################mod._optimizer.set_lr_mult({'conv1_weight':0})              # 单个多次指定->失败mod._optimizer.set_lr_mult({'conv1_bias':0})  mod._optimizer.sym.list_arguments()#['data', 'conv1_weight']mod._optimizer.sym.attr_dict()#{'conv1': {'no_bias': 'True', 'kernel': '(3, 3)', 'num_filter': '1'}, 'conv1_weight': {'no_bias': 'True', 'kernel': '(3, 3)', 'num_filter': '1'}}###   test   ###############mod.forward(mx.io.DataBatch([bch_kernel]))mod.get_outputs()[0].asnumpy()#array([[[[ 0.06028102]]]], dtype=float32)mod.backward()mod.update()mod.backward()mod.update()mod.backward()mod.update()mod.backward()mod.update()mod.forward(mx.io.DataBatch([bch_kernel]))mod.get_outputs()[0].asnumpy()#array([[[[-1.61971903]]]], dtype=float32)    !test failed###################################################################   Solution II  ############################################################################mod._optimizer.set_lr_mult({'conv1_bias':0,'conv1_weight':0})  # 一次指定完成mod._optimizer.sym.list_arguments()#['data', 'conv1_weight']mod._optimizer.sym.attr_dict()#{'conv1': {'no_bias': 'True', 'kernel': '(3, 3)', 'num_filter': '1'}, 'conv1_weight': {'no_bias': 'True', 'kernel': '(3, 3)', 'num_filter': '1'}}###   test   ###############mod.forward(mx.io.DataBatch([bch_kernel]))mod.get_outputs()[0].asnumpy()#array([[[[ 0.06028102]]]], dtype=float32)mod.backward()mod.update()mod.backward()mod.update()mod.backward()mod.update()mod.backward()mod.update()mod.forward(mx.io.DataBatch([bch_kernel]))mod.get_outputs()[0].asnumpy()#array([[[[ 0.06028102]]]], dtype=float32)    !test OK~

Jul 31, 2018

最近又要用到这方面的借口了,现在是gluon的江湖,一切向之看齐。
gluon推出了两个关于优化的接口,一个是固有的 optimizer,另一个是新加入的Trainer
通常同Trainer作为训练时的接口,但这两个类都接受Opt的参数,于是要检查下之前的设置是否合适。

  1. Trainer在step时调用optimizer中的updater,在update中,首先调用_get_lr获得Paramlr*:
#  _get_lr(self, index):  from optimizer.py    ¦   if index in self.param_dict:                                              ¦   ¦   lr *= self.param_dict[index].lr_mult     ¦   elif index in self.lr_mult:                                               ¦   ¦   lr *= self.lr_mult[index]                                                                                                                            ¦   elif index in self.idx2name:                                              ¦   ¦   lr *= self.lr_mult.get(self.idx2name[index], 1.0)

所以直接在ParamDict里面设置就好:

:

import mxnet as mxmodel = mx.gluon.nn.Sequential()with model.name_scope():    model.add(mx.gluon.nn.Embedding(30, 10))    ¦   model.add(mx.gluon.rnn.LSTM(20))    ¦   ¦   model.add(mx.gluon.nn.Dense(5, flatten=False))d1 = model.collect_params()model = mx.gluon.rnn.SequentialRNNCell()with model.name_scope():    model.add(mx.gluon.rnn.LSTMCell(20))    ¦   model.add(mx.gluon.rnn.LSTMCell(20))d2 = model.collect_params()d =  mx.gluon.ParamDict()d1.setattr('lr_mult',.01)    # 直接设置 lr_multd2.setattr('lr_mult',10)d.update(d1)d.update(d1)d['sequential0_dense0_weight'].lr_mult   #  合并后无影响d['sequentialrnncell0_lstm0_i2h_weight'].lr_mult

推测mxnet一贯使用引用手法,所以直接合并几个model的ParamDict,不会影响,但合并对于使用统一的Trainer接口却是必要的(不然会需要多个Trainer对应不同的model part)。

转载于:https://www.cnblogs.com/chenyliang/p/7451824.html

你可能感兴趣的文章
张季跃 201771010139《面向对象程序设计(java)》第四周学习总结
查看>>
如何解除循环引用
查看>>
android中fragment的使用及与activity之间的通信
查看>>
jquery的contains方法
查看>>
python3--算法基础:二分查找/折半查找
查看>>
Perl IO:随机读写文件
查看>>
转:基于用户投票的排名算法系列
查看>>
[转]ASP数组全集,多维数组和一维数组
查看>>
逻辑运算和while循环.
查看>>
linux后台运行和关闭SSH运行,查看后台任务
查看>>
cookies相关概念
查看>>
CAN总线波形中ACK位电平为什么会偏高?
查看>>
MyBatis课程2
查看>>
桥接模式-Bridge(Java实现)
查看>>
svn客户端清空账号信息的两种方法
查看>>
springboot添加servlet的两种方法
查看>>
java的Array和List相互转换
查看>>
layui父页面执行子页面方法
查看>>
如何破解域管理员密码
查看>>
Windows Server 2008 R2忘记管理员密码后的解决方法
查看>>