[深度学习]循环神经网络:RNN,LSTM,GRU,Attention机制,沿时间的截断反向传导算法

RNN(Recurrent Neural Network,循环神经网络)

 

每个RNN都有一个循环核心单元。它把x作为输入,将其传入RNN。RNN有一个内部隐藏态(internal hidden state)。这个隐藏态会在RNN每次读取新的输入时更新,然后隐藏态会将结果返回至模型。

其中,xt为t时刻的输入,ht为t时刻的内部隐藏态。

RNN相当于把许多循环神经网络单元连接成一个序列。可以设想梯度流穿过,当我们要计算关于h0的损失函数的梯度时,反向传播需要经过RNN中的每一个单元。每次反向传播经过一个单元时,都要使用其中某一个W的转置。

这意味着最终的表达式对h0梯度的表达式将会包含很多很多权重矩阵因子,这样不断对同一个值做乘法,是非常糟糕的。

在标量情况下,要么当这个值的绝对值大于1时,发生梯度爆炸;要么当这个值的绝对值小于1时,发生梯度消失,直到为0。既不发生梯度爆炸也不发生梯度消失,也就是当这个值正好为1。

对于矩阵而言,需要关注矩阵的最大奇异值,如果最大奇异值大于1,会发生梯度爆炸;如果最大奇异值小于1,会发生梯度消失。

用来解决梯度爆炸问题:梯度截断。

在外面计算梯度后,如果L2范式大于某个阈值,就将它剪断并做除法,这样梯度就有最大阈值。

用来解决梯度消失问题:使用更加复杂的RNN结构,例如LSTM。

 

LSTM(Long Short-Term Memory,长短期记忆网络)

LSTM可以用来缓解梯度消失和梯度爆炸问题。它在每个时间步中都维持两个隐藏状态,一个是ht,一个是ct。ct,也就是单元状态,相当于保留在LSTM内部的隐藏状态,并且不会暴露在外部去。

LSTM包含四个门,通过使用更好的结构,来获取更好的梯度流动:

1.forget gate:遗忘门,用来决定是否擦除一个cell;

2.input gate:输入门,用来决定是否写一个cell;

3.gate gate:用来决定对一个cell写多少;

4.output gate:用来决定对一个cell输出多少。

LSTM能尽量避免梯度爆炸或者梯度消失的原因有两个:

1.这里的遗忘门是矩阵元素相乘,而不是矩阵相乘。

2.矩阵元素相乘,可能会在不同的时间点乘以一个不同的遗忘门。

3.遗忘门是一个sigmoid函数,所以矩阵元素相乘的结果,会保证在(0,1)之间。

4.从最后的隐藏单元状态,反向传播到第一个单元状态,在反向传播的路径上,我们只通过一个单一的非线性tanh向后传播,而不是在每一个时间步长中单独设置tanh函数。

 

GRU(Gated recurrent unit,门控循环单元)

GRU只有两个门,分别为更新门和重置门,即图中的zt和rt。

更新门用于控制前一时刻的状态信息被带入到当前状态中的程度,更新门的值越大说明前一时刻的状态信息带入越多。

重置门用于控制忽略前一时刻的状态信息的程度,重置门的值越小说明忽略得越多。

思想:通过加法连接和乘法门来管理梯度流的理念,是非常有用的。

 

Attention Mechanism

注意力机制的定义:当我们人在看一样东西的时候,我们当前时刻关注的一定是我们当前正在看的这样东西的某一地方,换句话说,当我们目光移到别处时,注意力随着目光的移动野在转移,这意味着,当人们注意到某个目标或某个场景时,该目标内部以及该场景内每一处空间位置上的注意力分布是不一样的。这一点在如下情形下同样成立:当我们试图描述一件事情,我们当前时刻说到的单词和句子和正在描述的该事情的对应某个片段最先关,而其他部分随着描述的进行,相关性也在不断地改变。

为什么要使用注意力机制:

上图展示的Encoder-Decoder模型是没有体现出“注意力模型”的,所以可以把它看作是注意力不集中的分心模型。为什么说它注意力不集中呢?请观察下目标句子Y中每个单词的生成过程如下:

                                           

其中f是decoder的非线性变换函数。从这里可以看出,在生成目标句子的单词时,不论生成哪个单词,是y1,y2也好,还是y3也好,他们使用的句子X的语义编码C都是一样的,没有任何区别。而语义编码C是由句子X的每个单词经过Encoder 编码产生的,这意味着不论是生成哪个单词,y1,y2还是y3,其实句子X中任意单词对生成某个目标单词yi来说影响力都是相同的,没有任何区别(其实如果Encoder是RNN的话,理论上越是后输入的单词影响越大,并非等权的,估计这也是为何Google提出Sequence to Sequence模型时发现把输入句子逆序输入做翻译效果会更好的小Trick的原因)。这就是为何说这个模型没有体现出注意力的缘由。这类似于你看到眼前的画面,但是没有注意焦点一样。如果拿机器翻译来解释这个分心模型的Encoder-Decoder框架更好理解,比如输入的是英文句子:Tom chase Jerry,Encoder-Decoder框架逐步生成中文单词:“汤姆”,“追逐”,“杰瑞”。在翻译“杰瑞”这个中文单词的时候,分心模型里面的每个英文单词对于翻译目标单词“杰瑞”贡献是相同的,很明显这里不太合理,显然“Jerry”对于翻译成“杰瑞”更重要,但是分心模型是无法体现这一点的,这就是为何说它没有引入注意力的原因。没有引入注意力的模型在输入句子比较短的时候估计问题不大,但是如果输入句子比较长,此时所有语义完全通过一个中间语义向量来表示,单词自身的信息已经消失,可想而知会丢失很多细节信息,这也是为何要引入注意力模型的重要原因。

上面的例子中,如果引入AM模型的话,应该在翻译“杰瑞”的时候,体现出英文单词对于翻译当前中文单词不同的影响程度,比如给出类似下面一个概率分布值:

(Tom,0.3)(Chase,0.2)(Jerry,0.5)

每个英文单词的概率代表了翻译当前单词“杰瑞”时,注意力分配模型分配给不同英文单词的注意力大小。这对于正确翻译目标语单词肯定是有帮助的,因为引入了新的信息。同理,目标句子中的每个单词都应该学会其对应的源语句子中单词的注意力分配概率信息。这意味着在生成每个单词Yi的时候,原先都是相同的中间语义表示C会替换成根据当前生成单词而不断变化的Ci。理解AM模型的关键就是这里,即由固定的中间语义表示C换成了根据当前输出单词来调整成加入注意力模型的变化的Ci。增加了AM模型的Encoder-Decoder框架理解起来如图2所示。

   

                                             图2 引入AM模型的Encoder-Decoder框架

即生成目标句子单词的过程成了下面的形式:

                                               

而每个Ci可能对应着不同的源语句子单词的注意力分配概率分布,比如对于上面的英汉翻译来说,其对应的信息可能如下:

                      

其中,f2函数代表Encoder对输入英文单词的某种变换函数,比如如果Encoder是用的RNN模型的话,这个f2函数的结果往往是某个时刻输入xi后隐层节点的状态值;g代表Encoder根据单词的中间表示合成整个句子中间语义表示的变换函数,一般的做法中,g函数就是对构成元素加权求和,也就是常常在论文里看到的下列公式:

                                           

假设Ci中那个i就是上面的“汤姆”,那么Tx就是3,代表输入句子的长度,h1=f(“Tom”),h2=f(“Chase”),h3=f(“Jerry”),对应的注意力模型权值分别是0.6,0.2,0.2,所以g函数就是个加权求和函数。如果形象表示的话,翻译中文单词“汤姆”的时候,数学公式对应的中间语义表示Ci的形成过程类似下图:

          

                                        

                                                                         图3 Ci的形成过程

这里还有一个问题:生成目标句子某个单词,比如“汤姆”的时候,你怎么知道AM模型所需要的输入句子单词注意力分配概率分布值呢?就是说“汤姆”对应的概率分布:

(Tom,0.6)(Chase,0.2)(Jerry,0.2)

是如何得到的呢?

为了便于说明,我们假设对图1的非AM模型的Encoder-Decoder框架进行细化,Encoder采用RNN模型,Decoder也采用RNN模型,这是比较常见的一种模型配置,则图1的图转换为下图:

                                                                        图4 RNN作为具体模型的Encoder-Decoder框架

那么用下图可以较为便捷地说明注意力分配概率分布值的通用计算过程:

                                     

                                                                                 图5 AM注意力分配概率计算

对于采用RNN的Decoder来说,如果要生成yi单词,在时刻i,我们是可以知道在生成Yi之前的隐层节点i时刻的输出值Hi的,而我们的目的是要计算生成Yi时的输入句子单词“Tom”、“Chase”、“Jerry”对Yi来说的注意力分配概率分布,那么可以用i时刻的隐层节点状态Hi去一一和输入句子中每个单词对应的RNN隐层节点状态hj进行对比,即通过函数F(hj,Hi)来获得目标单词Yi和每个输入单词对应的对齐可能性,这个F函数在不同论文里可能会采取不同的方法,然后函数F的输出经过Softmax进行归一化就得到了符合概率分布取值区间的注意力分配概率分布数值。图5显示的是当输出单词为“汤姆”时刻对应的输入句子单词的对齐概率。绝大多数AM模型都是采取上述的计算框架来计算注意力分配概率分布信息,区别只是在F的定义上可能有所不同。

上述内容就是论文里面常常提到的Soft Attention Model的基本思想,你能在文献里面看到的大多数AM模型基本就是这个模型,区别很可能只是把这个模型用来解决不同的应用问题。那么怎么理解AM模型的物理含义呢?一般文献里会把AM模型看作是单词对齐模型,这是非常有道理的。目标句子生成的每个单词对应输入句子单词的概率分布可以理解为输入句子单词和这个目标生成单词的对齐概率,这在机器翻译语境下是非常直观的:传统的统计机器翻译一般在做的过程中会专门有一个短语对齐的步骤,而注意力模型其实起的是相同的作用。在其他应用里面把AM模型理解成输入句子和目标句子单词之间的对齐概率也是很顺畅的想法。

soft attention:采用的是加权组合所有图像位置中的所有特征

hard attention:限制模型在每一步只选择一个位置来关注图像。在hard attention的模式下,选择attention的位置有点复杂,因为这不是一个可微函数。

Truncated Back Propagation througn time (沿时间的截断反向传导算法)

即使我们输入的序列很长很长,甚至趋近于无限,采用的方法是:

在训练模型时,向前计算若干步(如100步)子序列的损失值,然后沿着这个序列反向传播误差,并计算梯度更新参数。

计算下一批数据的梯度时,只根据前一批数据反向传播误差。前向计算和反向传播,都只是持续一定数量的时间步。

猜你喜欢

转载自blog.csdn.net/u013250416/article/details/81276671