深度学习之三:RNN

RNN,也就是Recurrent Neural Network,循环神经网络,是非线性动态系统,将序列映射到序列,主要参数有五个:[Whv, Whh, Woh, bh, bo, h0] ,典型的结构图如下:



解释一下上图:

  • 和普通神经网络一样,RNN有输入层输出层和隐含层,不一样的是RNN在不同的时间t会有不同的状态,其中t-1时刻隐含层的输出会作用到t时刻的隐含层
  • [Whv, Whh, Woh, bh, bo, h0]的参数意义是: Whv:输入层到隐含层的权重参数,Whh:隐含层到隐含层的权重参数,Woh:隐含层到输出层的权重参数,bh:隐含层的偏移量,bo输出层的偏移量,h0:起始状态的隐含层的输出,一般初始为0  
  • 不同时间的状态共享相同的权重w和偏移量b

RNN的计算方式

 


之前看过了一般神经网络和CNN,再看RNN其实觉得结构并不复杂, 计算过程看起来的话,RNN的计算方式和普通的前馈算法也没有什么大的区别,不过是上一时刻的隐含层的输出结果又在现在时刻的计算过程里面用到了,也就是不断传递的过程,这也就是为什么RNN是从序列到序列,一个状态的出入和前面几个状态的输出都有关系。

 

给定一个损失函数L:



 
当然不同的神经网络对应的训练方法也不一样, RNN因为加入了时间序列,因此训练过程也是和之前的网络不一样,RNN的训练使用的是BPTT(Back Prropagation Through TIme),该方法是由Werbo等人在1990年弄出来的

 

具体的训练过程如下:



  
上面的算法也就是求解梯度的过程,使用的也是经典的BP算法,并没有什么新鲜的,但是值得一提的是,在 t-1  时刻对  ht1的求导值,也需加上 t 时刻的求导中对  ht1 的求导值,因此BPTT也是一个链式的求导过程

 

但是因为上面算法中的第10行,在训练t时刻的时候,出现了t-1的参数,因此对单个的求导就变成了对整个之前状态的求导之和,比如说我们在T时刻对Whh求导,计算公式如下:

 

 

 

 也正是因为存在长依赖关系,BPTT无法解决长时依赖问题(即当前的输出与前面很长的一段序列有关,一般超过十步就无能为力了),因为BPTT会带来所谓的梯度消失或梯度爆炸问题(the vanishing/exploding gradient problem)。这篇文章很好的解释了为什么会产生梯度消失和为什么会梯度爆炸的问题,其实主要问题就是因为在BPTT算法中,以w为例,其求导过程的链太长,而太长的求导链在以tanh为激活函数(其求导值在0~1之间的BPTT中,连乘就会使得最终的求导为0,这就是梯度消失问题,也就是t时刻已经学习不到t-N时刻的参数了。当然,有很多方法去解决这个问题,如LSTMs便是专门应对这种问题的,还有一些方法,比如设计一个更好的初始参数以及更换激活函数(如换成ReLU激活函数)。

 以上就是经典的RNN模型以及推导过程,最近几年依赖RNN有了很多的变体和拓展,详见:RNNs扩展和改进模型

 

 

 

参考文献:

【1】SutskEver,Training Recurrent Neural Networks.PhD thesis,Univ.Toronto(2012)

【2】循环神经网络(RNN, Recurrent Neural Networks)介绍

 


 

猜你喜欢

转载自luchi007.iteye.com/blog/2285940