传统Seq2Seq+Attention实现机器翻译

实验软件和硬件环境:

1、 硬件环境:

个人PC
华为云 modelArts 云计算资源 CPU:8核 64GiB+GPU:1 * nvidia-p100

2、 软件环境:

Python 3.7
Tensorflow 1.8.0
Anaconda3
完整代码及数据有待更新上传


声明:创作不易,未经授权不得复制转载
statement:No reprinting without authorization


内容:

  1. 理解并实践神经机器翻译模型(英-中),用 TensorFlow 框架实现 seq2seq 神经网络中英文机器翻译模型
  2. 加入biRNN、Attention 机制并理解原理
  3. 比较不同模型的翻译结果,用 blue 指标评测翻译结果
    实验原理和方法:

一、基础模块原理介绍——Encoder到Decoder的Seq2Seq模型

Seq2Seq模型

(一)最基础的Seq2Seq模型包含了三个部分:

(1)Encoder
(2)Decoder
(3)连接两者的中间状态向量


Seq2Seq模型

Encoder通过学习输入,将其编码成一个固定大小的状态向量S,继而将S传给 Decoder,Decoder再通过对状态向量S的学习来进行输出。每一个box代表了一个RNN单元,通常是LSTM或者GRU

(二)传统seg2sea弊端:

1、编码为固定大小状态向量的过程实际上是一个信息“信息有损压缩”过程
2、随着sequence length的增加,意味着时间维度上的序列很长,RNN模型也会出现梯度弥散(使用LSTM或GRU解决),而且当输入序列非常长时,模型难以学到合理的向量表示。
3、连接Encoder和Decoder模块的仅仅是一个固定大小的状态向量,这使得Decoder无法直接去关注到输入信息的更多细节。

(三)改进:

加入Attention、Bi-directional encoder layer等

一、基础模块原理介绍——attention 和 biRNN 简单介绍

• Attention机制:打破了传统编码器-解码器结构在编解码时都依赖于内部一个固定长度向量的限制。
• 通过保留encoder对输入序列的中间输出结果,然后训练一个模型来对这些输入进行选择性的学习,并且在模型输出时将输出序列与之进行关联。
• 通俗的解释: attention机制就是将encoder的每一个隐藏状态设定一个权重,根据权重的不同决定decoder输出更侧重于哪一个编码状态。
• biRNN:使得当前的输出不仅可以利用之前的序列元素的信息,还可以依赖之后的序列元素的信息;对于NMT而言能充分利用“上下文”信息,提升翻译效果。

右为加入Attention

二、代码实现细节介绍 ——data set 数据集

• 中英平行语料:train.txt 80000对中英文平行语料 + valid.txt 2500对中英文平行语料
• 训练数据统计信息:

• -----English Text-----

• Number of sentences: 80000
• Average number of words in a sentence: 24.446491070178595
• Max number of words in a sentence: 54

• -----Chinese Text-----

• Number of sentences: 80000
• Average number of words in a sentence: 24.778384432311352
• Max number of words in a sentence: 96

• 中英平行语料:train.txt 80000对中英文平行语料 + valid.txt 2500对中英文平行语料
• 训练数据统计信息:

• 分词处理:

• 英文分词:使用NLTK工具包(nltk-3.4) 中文分词:使用pyltp工具包(0.2.1)

二、代码实现细节介绍——encoder端双向rnn代码实现

• 主要核心函数代码(基于tensorflow强大的工具包):
构建RNN单元:

single_cell = tf.contrib.rnn.BasicLSTMCell(num_units, forget_bias=forget_bias) 
# or tf.contrib.rnn.GRUCell(num_units)       [num_units为单元输出向量维度]
single_cell = tf.contrib.rnn.DropoutWrapper(cell=single_cell,input_keep_prob=1.0-dropout)  
# 可用来将dropout应用到rnn单元上

拼接构成biRNN:

num_bi_layers = num_layers // 2
fw_cell = self._build_encoder_cell(hparams, num_bi_layers)
bw_cell = self._build_encoder_cell(hparams, num_bi_layers)

bi_outputs, bi_state = tf.nn.bidirectional_dynamic_rnn(
                    fw_cell, bw_cell, encoder_emb_in, dtype=scope.dtype,
                    sequence_length=self.iterator.source_sequence_length,
                    time_major=True, swap_memory=True)
                
encoder_outputs = tf.concat(bi_outputs, -1)
bi_encoder_state = bi_state

Tf实现birnn的思想也很简单:


image.png

其实本质就是做了两次reverse:
• 第一次reverse:将输入序列进行reverse,然后送入dynamic_rnn做一次运算.
• 第二次reverse:将上面dynamic_rnn返回的outputs进行reverse,保证正向和反向输出 对应位置的 输入是一致的 是对上的.
• 最后合并output元组返回

二、代码实现细节介绍——Attention和Beam Search代码实现

Tf提供了库包装函数:

attention_mechanism = tf.contrib.seq2seq.LuongAttention( )
cell = tf.contrib.seq2seq.AttentionWrapper(cell, attention_mechanism,
                                                   attention_layer_size=num_units,
                                                   alignment_history=alignment_history,
                                                   output_attention=True,
                                                   name='attention')
my_decoder  = tf.contrib.seq2seq.BeamSearchDecoder(cell=cell, embedding …beam_width…)

二、代码实现细节介绍——对于Attention的理解与实现原理

• 将之前传统的只将最后一个rnn单元的输出传递给decoder,改为将序列上的每一个单元的输出信息都进行传递,并加以权重让其对decoder端的每个单元的输出产生影响。
• 通过在encoder和decoder之间构造一个隐藏的全连接网络来实现,将encoder的outputs输入该网络,输出权重信息(不同权重表示不同的attention),并在反向传播的同时也更新该全连接网络的权重,直到其生成的attention信息能很好的指导decoder解析生成正确的字符。
• Attention机制会使网络的参数增加,训练难度增加且更不易收敛,但其带来的收益也很大。

二、代码实现细节介绍——attention实现代码分析

image.png

补充:Teacher forcing 技巧——feeding the target as the next input (decoder序列位置1上输入字符,而后每个位置上的输入并不以前一步的输出作为输入而是将真实值输入,可加快训练。

二、代码实现细节介绍——Beam Search集束搜索和mask

• Beam Search(集束搜索):在decoder解码选择单词时,每次只考虑前top B个结果,例如先找到句子第一个词的最可能B种,而后假设字典大小为10000,B=3,第二步时就有10000x3=30000种可能,选择前三种。B = 1时相当于贪婪搜索。
• Loss+mask:因为一个batch中句子的长度通常是不一样的,一个batch中不足长度的位置需要进行填充(pad)补0,最后生成句子计算loss时需要忽略那些原本是pad的位置的值,即只保留mask中值为1位置的值,忽略值为0位置的值。
• 函数:tf.sequence_mask()

三、实际训练调参及结果对比——可调的参数

•   是否加入attention
•   是否使用 birnn 构造 encoder
•   Encoder的层数
•   src_max_len:输入句子序列最大长度
•   tgt_max_len:输出句子序列最大长度
•   num_units:rnn单元输出维度
•   Optimizer:优化方法(sgd/adam)
•   learning_rate:学习率
•   num_train_steps:训练总轮数
•   init_weight:网络参数初始化权重参数
•   unit_type: LSTM or GRU
•   forget_bias:rnn单元参数初始化偏置
•   Dropout:(0.0 —1.0)
•   batch_size:批大小
•   beam_width:集束宽

三、实际训练调参及结果对比——一些影响较小的参数最优值

•    self.src_max_len = 50
•    self.tgt_max_len = 35
•    self.optimizer = ‘sgd’ (相比于自适应的跟可靠些)
•   self.num_train_steps = 50000
•    self.init_weight = 0.1
•    self.dropout = 0.2
•    self.batch_size = 128
•    self.beam_width = 5(训练时知道最优解用不到)
•     self.learning_rate = 0.2 (使用了learning_rate_decay,训练时会自动动态调整)
•    self.forget_bias = 1.0

三、实际训练调参及结果对比——结果对比

result

三、实际训练调参及结果对比——结果分析

• 1、attention 和 biRnn 的使用较显著的提升了结果。
• 2、适当的增加网络层数以及LSTM单元内部计算向量维度(也是输出维度num_units)能够对结果有一些提升,但是对于数据集较小时,不易太大,否则会不收敛等
• 3、RNN感觉还是比较神奇的,其训练也比其它网络一般更费时,一般都得10个epoch以上才完整收敛,但其实最终的模型大小也就几十M一般,不像一个cnn随便就上百M(可能受益于rnn单元的参数共享)。

三、实际训练调参及结果对比——部分结果展示

image.png

四、GUI设计与展示

• 利用pyqt搭建一个简单的Chinese-English的NMT应用,可以对输入的中文或英文利用已经训练好的model进行翻译。
• 输入示例:
• Chinese: 这件紧身T恤衫可显现你结实、线条优美的手臂和性感的肩膀。


image.png

• 输入示例:
• English: all our winchman are well trained and'skilled'skilful proficient practiced in handling winches .


image.png

五、实际训练调参及结果对比——Reference参考资料

1、理论知识参考

https://zhuanlan.zhihu.com/p/37148308 (传统Seq2Seq )
https://zhuanlan.zhihu.com/p/40920384 (Seq2Seq Attention模型)
https://zhuanlan.zhihu.com/p/37290775 (attention + birnn)
https://zhuanlan.zhihu.com/p/36029811?group_id=972420376412762112 (beam search)
https://blog.csdn.net/uhauha2929/article/details/83019995 (mask_loss)

2、代码参考:

https://github.com/VectorFist/RNN-NMT
https://github.com/OpenNMT/OpenNMT-tf
https://github.com/tensorflow/tensorflow/blob/master/tensorflow/https://github.com/tensorflow/tensorflow/blob/master/tensorflow/contrib/eager/python/examples/nmt_with_attention/nmt_with_attention.ipynb
https://github.com/NELSONZHAO/zhihu/tree/master/mt_attention_birnn

你可能感兴趣的:(传统Seq2Seq+Attention实现机器翻译)