诚信为本:市场永远在变,诚信永远不变。

摩杰资讯

当前位置: 首页 > 摩杰资讯

摩杰资讯

发布时间:2024-03-04 13:01:03点击量:

这篇文章跟大家分享下THOR的实践应用。THOR算法的部分内容当前已经在MindSpore中开源,源码位置:

https://gitee.com/mindspore/mindspore/blob/master/mindspore/nn/optim/thor.py

MindSpore中使用THOR训练网络非常简单,下面用四行代码先来带大家看一下怎么使用。


  • 导入二阶优化器THOR所需要的包

  • 第一行代码常规创建网络
  • 第二行代码定义我们使用的优化器THOR
  • 第三行代码是为了增加计算图从而使THOR达到更优性能
  • 第四行代码训练网络

我们再具体展开介绍下。首先导入MindSpore所需的二阶优化器的包,位于 mindspore.nn.optim

然后创建你所需的网络;接着定义THOR优化器,传入网络信息和THOR所需的超参信息(如学习率,正则化项系数等);

调用 convert_to_thor_model函数,该函数是通过增加计算图使THOR达到更优性能,什么意思呢,本身网络运行的时候是一张计算图,THOR中会使用过时的二阶信息,通过额外增加一张计算图,两张计算图分别执行更新二阶矩阵和不更新二阶矩阵的操作从而达到更优性能(PS. MindSpore支持动静态图,在这里为了更好的性能使用的是静态图模式,对这块内容比较感兴趣的同学,可以点这个链接:https://mindspore-website.obs.cn-north-4.myhuaweicloud.com/white_paper/MindSpore_white_paper.pdf);

最后,调用model.train就可以开始训练啦。简单介绍了下怎么使用,接下来我们来看下它的源码。


源码分析

init 函数用于THOR的初始化,需要传入THOR所需的超参和网络结构,THOR支持GPU和Ascend,分别为class THOR_GPU(Optimizer)和  class THOR_Ascend(Optimizer)这两个类之间的主要差别是算子不同。下面我们以 class THOR_Ascend(Optimizer)为例,来分析一下。
 
 

MindSpore中所有优化器都继承了 class Optimizer,该基类中定义了一些基本函数(如获取学习率,梯度缩放等)。THOR初始化时将传进去的超参定义为类属性方便调用,并且定义了后续计算会使用到的算子。


也就是说初始化函数的作用就是定义THOR计算所需要用到的算子和变量(ParameterTensor等)。

重点介绍下  self.matrix_A_cov ,  self.matrix_G_cov 。这两个变量是计算二阶梯度所需要的信息,分别为每层输入  的协方差矩阵  和每层输出的一阶导数  的协方差矩阵  ,其中  已经在运行时的前向过程和反向过程中保存下来。

我们再来看下创建THOR时的入参:

net:本次训练建立的模型;

learning_rate:学习率超参;
damping:二阶矩阵中加的正则化项的超参;
momentum:动量超参;
weight_decay:权值衰减,用于防止过拟合,默认值为0.0,即不使用权值衰减;
loss_scale:用于缩放训练过程中的loss,防止梯度越界,默认值为1.0,即不使用缩放;
batch_size:当前训练一个step所使用的数据量,默认为32;
decay_filter:选择对哪些层做weight decay,当weight_decay>0时起作用;
split_indices:这个参数的作用是用于加速allreduce过程。

_get_Ainv_Ginv_Amax_Gmax_list函数用于计算协方差矩阵A/G的逆,并返回求完逆后的矩阵。具体过程是遍历模型所有层,按层处理,对每一层的协方差矩阵加上正则化项,然后对矩阵进行cholesky分解从而来求逆。当前开源代码THOR中支持全连接层和卷积层的处理。

 
 
_get_second_gradients函数用于计算最终参数更新方向,在论文中参数更新方向公式为 ,所以代码实际实现的方式为 ,代码如下
 
  

construct函数是在网络训练过程中会实际执行的内容,该函数中包含了上述两个函数_get_Ainv_Ginv_Amax_Gmax_list_get_second_gradients的调用,该函数完成了二阶矩阵的计算和梯度更新方向的调整。

 
   
   
  


在这一节中跟大家分享下THOR的实践应用,举了两个例子分别为ResNet50和BERT,这两个例子的代码也已开源,链接如下:
ResNet50:https://gitee.com/mindspore/mindspore/blob/master/model_zoo/official/cv/resnet/train.py
BERT:
https://gitee.com/mindspore/mindspore/blob/master/model_zoo/official/nlp/bert/run_pretrain.py


ResNet50[1] 

优化器的调用方式与文中开头提到的一致,在这个例子中把具体训练过程给展开了。

首先创建了网络训练需要的训练集和网络定义为ResNet50;
随后设置THOR所需要用到的超参策略,其他超参值设定可去该目录下的src/config.py中修改;
接着创建THOR优化器,并传入设置的超参值;
然后转换模型保存二阶所需信息;
最后就可以训练网络了。
 
   

最后输入

即可运行脚本啦。
 BERT[2] 

BERT中步骤与ResNet50差不多。首先创建了网络训练需要的训练集和网络定义为BERT;随后设置THOR所需要用到的超参策略,其他超参值设定可去该目录下的src/config.py中修改;优化器创建时传入BERT设定的超参值,本例中创建时传入了:

表示做weight decay操作时排除LN层和FC中的bias参数;然后转换模型保存二阶所需信息;最后就可以训练网络了。

 
   

最后输入 

即可运行脚本啦.至此高阶优化器系列的内容就结束啦,该系列总共有三篇文章分别从优化器的背景,MindSpore自研优化器的介绍和MindSpore 高阶优化器THOR 的源码分析&实践应用这三个内容来跟大家分享,如有不足之处欢迎大家批评指正。同时也欢迎大家到MindSpore开源社区中一起玩耍。

参考文献:

[1]He K, Zhang X, Ren S, et al. Deep residual learning for image recognition[C]//Proceedings of the IEEE conference on computer vision and pattern recognition. 2016: 770-778.

[2]Devlin J, Chang M W, Lee K, et al. Bert: Pre-training of deep bidirectional transformers for language understanding[J]. arXiv preprint arXiv:1810.04805, 2018.

了解完MindSpore的关键技术是不是很心动呢!赶紧【点击链接】并【立即报名】,即可在 ModelArts 平台学习到一个经典案例掌握基于MindSpore的深度学习!

平台注册入口