seq2seq详细总结

tech2022-08-08  126

1.前言

seq2seq属于encoder-decoder结构的一种,基本思想就是利用两个RNN,一个RNN作为encoder,另一个RNN作为decoder。 为什么不直接使用一个 RNN 呢?有一种RNN结构是 many to many, 但它只适用于输出序列的长度和输入序列的长度相等的情况,结构图如下 seq2seq框架很好地解决了这个问题

seq2seq介绍:

seq2seq模型,全称Sequence to sequence,由Encoder和Decoder两个部分组成,每部分都是一个RNNCell(RNN、LSTM、GRU等)结构。Encoder将一个输入序列编码为一个固定长度的语义向量c,c可以表示输入句子的语义信息,Decoder将该语义向量解码为另一个序列。

特点:输入序列和输出序列的长度是可变的,输出序列长度可以不等于输入序列长度。 应用:比如机器翻译、聊天,问答系统等

seq2seq有两种常见的框架,下面逐一介绍:

2. seq2seq框架1

该框架由这篇论文提出:Sutskever et al.(2014) Sequence to Sequence Learning with Neural Networks。结构图如下 输入序列是:x1, x2, x3, x4。 输出序列是 y1, y2, y3 encoder负责将输入序列压缩成指定维度的向量c,这个向量就可以看成是这个序列的语义信息了,这个过程称为编码。 这个框架的特点:在decoder部分, 上一时刻的输出y_t-1会作为当前时刻的输入,而且语义向量c只作为初始隐层状态参与运算,后面的运算都与语义向量C无关.

Encoder 获取语义向量c最简单的方式就是: ①直接将输入序列最后一个时刻的隐藏状态作为语义向量C;②也可以对最后一个隐含状态做一个维度变换得到指定维度的语义向量c。具体看这两个方法: 假设:RNNCell 就是简单的 RNN

① W,V是权值矩阵,可以学习得到,[ ]中括号表示拼接 h_t 是输入序列每个时刻 t 的隐层状态,y_t 是输入序列每个时刻 t 的输出(后面并不要它) 我们要一直计算到最后一个时刻 h_T的隐层状态值,令 h_T = c ② 假设我们只要50 维的 c 向量,而 h_T 是 100 维,怎么办呢? 我想大家都能想到就是接一个线性层(假设线性层权重是 Wc),因为得到的值有大有小,我们用 tanh 函数把它归一化到0均值,也就是(-1,1)之间。注意:当RNNCell 就是简单的 LSTM时不需要tanh,因为这个模型输出就是tanh后的。公式如下

Decoder 接收到Encoder来的语义向量 c,首先输入一个开始信号y0(比如为 < START>),然后计算 h1’ ,当然不能直接把< START>输进去,要输入它的embedding向量

W,V是权值矩阵,可以学习得到,[ ] 中括号表示拼接 h_1‘ 是输出序列的初始隐层状态,y_1’ 是输出序列初始时刻的概率分布,向量中的每个值是对应单词的概率,为|V|维向量,|V|为词库大小 o_1是 y_1中最大概率值对应的单词 e(o_1) 是单词 o_1 的embedding 向量 有了 h_1’ 和 y_1’,剩下时刻按照如下公式计算 可以看到剩余时刻,c 都是没有参与的 直到预测值为 < END > 时结束预测。 画个图,便于大家理解输入的关系

3.seq2seq 框架2

该框架由论文Cho et al.(2014) Learning Phrase Representations using RNN Encoder–Decoder for Statistical Machine Translation 结构图如下: 这个模型的特点:语义向量C参与了输出序列所有时刻的运算,如上图从c 出发的箭头既指向圆圈(就是decoder的隐层状态),又指向了输出 y 这篇论文的 RNNCeil 是 GRU,那么就以GRU为例

Encoder 如图: 我们要一直计算到最后一个时刻的隐层状态 h_T, 然后按① 或 ②的方法计算出语义向量c

Decoder 接收到Encoder来的语义向量 c,首先输入一个开始信号y0(比如为 < START>),然后计算 h1’ ,当然不能直接把< START>输进去,要输入它的embedding向量, 由于语义向量 c 作用于Decoder的每一时刻,可以把公式合并成一个 注意:不要弄混编码时的输出 y_t, 和解码时的输出 y_t’, 编码的输出 y_t我们是不要它的 上面公式中: [ ] 同样表示拼接,* 表示元素级别的乘法,要求符号两边矩阵维度相同 o_t 是 t 时刻的单词, e(o_t) 是单词 o_t 的 embedding向量 y_t’ 是 t 时刻的输出概率分布,向量中的每个值是对应单词的概率,维度为 |V|, |V|为词库大小 直到预测值为 < END > 时结束预测。 仍然画张图便于理解

4. seq2seq 的训练过程

我们以seq2seq框架2为例,假如要训练这样的数据 在Decoder部分,我们是可以计算出每个时刻的单词概率分布(维度为|V|), 只要把每个时刻的单词概率分布连乘,就可以得到我们的目标函数了 例如上图:X是输入序列“机器学习", 输出序列y1, y2 第一时刻:p(y1| X) = p(machine | < bos >, c) 第二时刻:p(y2| X) = p(learning | machine, c) 目标函数是:p(y1, y2| X) = p(machine | < bos >, c) ▪ p(learning | machine, c)(通常会转化为log形式)

用官方一点的话讲: 设有输入序列X(x1,x2,…,xT),输出序列Y(y1,y2,…yT’),输入序列和输出序列的长度可能不同即T 和 T‘ 可能不同。那么其实就需要根据输入序列去得到输出序列可能输出的词概率,于是有下面的条件概率:x1,x2,…,xT发生的情况下,y1,y2,…yT 发生的概率等于p( yt | y1, y2, …y_t-1, c) 的连乘 用公式表示目标函数:

现在问题是如何求 p( yt | y1,y2…y_t-1, c)的形式

下面直接上公式: 符号的意思跟上面说的一样; 这里 g 表示一个 softmax 层,其实就是下面这个概率。加上 ’ 只是为了区分Encoder 和 Decoder 部分,大家可以不用纠结于此

然后公式中出现了 h_t’,也直接上公式

符号的意思跟上面说的一样; 这里 f 取决于你用的RNNCeil , 比如 这里用 RGU, 那么 h_t’ 就是: 所以对于训练样本,我们要做的就是在整个训练样本下,所有样本的条件概率之和最大。对应的对数似然条件概率函数为 样本形式: < x, y >, x 是输入序列,y 是输出序列。 如样本 < 我 是 中国 人,l am chinease > yn: 第 n 个样本的输出序列,xn : 第 n 个样本的输入序列 最后:可以用交叉熵损失函数训练模型

最新回复(0)