基础的序列到序列 序列1到序列2,也叫一个序列对 (序列1,序列2) 在预测的时候,要求输入序列1,能输出序列2,序列2的预测过程大致是这样的: 根据序列1的信息,预测出序列2的第一个单词, 然后计算第一个单词在当前序列1的场景下,最大概率会出现哪个单词, 然后就这么一个单词一个单词却预测下去... 有人说如果第一个单词预测错了,那后面的就全完了... (有小概率,在错误的道路上再犯错,又回到正确道路上了...负负又得正了...仅人个观点...) 预测的序列是一个生成的过程,且依据的是概率... 也有人把这个过程比喻为“狗尾续貂”... 可以做的事情有: 翻译:标准的序列到序列 对话:对话机器人,尬聊,智能客服 信息提取:压缩,降维,文章摘要自动生成,自编码器 语音识别:声音信号转文本 无线信号处理 序列到序列+注意力 RNN提取特征, 注意力作为一个辅助 基于注意力的序列到序列 注意力提取特征, 整体流程与基础的序列到序列一致 transformer 注意力提取特征, 整体流程与基础的序列到序列 大致/大方向 一致 增加/改变了一些地方 |
下面这篇文章 以时间线 介绍了 传统NLP的发展历程,从最早的分词到2017年问世的transformer Transformer通俗笔记:从Word2Vec、Seq2Seq逐步理解到GPT、BERT |
|
|
|
数据的样子
import jieba seq1= "你现阶段的目标是?" seq2= "不上班还有钱花" sentence1 = jieba.lcut(seq1) word2id = {} word2id["PAD"] = 0 # 补长度 是为了批次处理 len_add = len(word2id) word2id.update({word:(index+len_add) for index,word in enumerate(set(sentence1))}) sentence2 = jieba.lcut(seq2) len_add = len(word2id) word2id.update({word:(index+len_add) for index,word in enumerate(set(sentence2))})
解码序列每个单词与编码序列所有单词的关系
sentence1 ['你', '现阶段', '的', '目标', '是', '?'] sentence2 ['不', '上班', '还有', '钱花'] 核心:求sentence2每个单词 相对sentence1所有单词的注意力/特征 输入:sentence1,sentence2 输出:[seq_len2,embedding_dim]矩阵,每个维数为embedding_dim的向量都是 sentence2相应单词 相对sentence1的特征向量
如此,编码序列的单词向量一定程度上包含有本身与整个句子之间的信息, 除了解码序列相对编码序列外, 还有解码序列相对解码序列,编码序列相对编码序列 这三组关系,也是需要去训练,让模型去学习的
解码序列前一个单词与后一个单词的关系
编码序列预测出 解码序列的第1个单词:['你', '现阶段', '的', '目标', '是', '?'] -- ['不'] 然后依次为: ['你', '现阶段', '的', '目标', '是', '?'] + ['不'] -- [ '上班'] ['你', '现阶段', '的', '目标', '是', '?'] + ['不', '上班'] -- ['还有'] ['你', '现阶段', '的', '目标', '是', '?'] + ['不', '上班', '还有'] -- ['钱花'] ['你', '现阶段', '的', '目标', '是', '?'] + ['不', '上班', '还有', '钱花'] -- OVER
解码序列相对解码序列的自注意力
补码的意义在于去掉PAD 编码序列的每个单词 对应编码序列的所有单词 但解码序列是 已知的所有单词生成下一个单词,再后面的单词是未知的,尚不清楚... 训练时拿到了全体数据库,是知道的,是程序员知道... 但训练的过程是生成式的,即参数学习...修改的过程...只涉及已生成的单词,程序只知道已生成的 你说程序还不是人设计的,就给它设计成提前知道所有单词,让参数直接学习解码器的所有单词, 在预测时,才使用已知单词,这样可以吗? 这是本人的另外一个猜测,尚未实验...但猜测是可行的,说不定更快... 未来大概率发生的事,大概率会成真... 预定的未来...
transformer的主逻辑
x0 -- 编码序列相对编码序列的自注意力 -- x1 y0 -- 解码序列相对解码序列的自注意力 -- y1 y1 相对x1 的注意力 y2 y2 -- 线性变换+激活函数处理 -- y3 y3 -- 全连接分类,映射到单词词典的标签索引上 -- y4 y4中最大值索引对应词典的单词,即模型要预测的单词
seq to seq简要回顾
seq to seq 是在RNN的基础上发展而来的, RNN的缺点是上下文依赖能力弱,它做出的改良方案是: 想办法让解码序列的每个元素带上编码序列的信息 实施细节 求编码序列的上下文向量,然后让解码序列的每个单词与 这个上下文向量,拼接,注意是拼接 效果 比RNN有明显提升,但仍然处理不了太长的序列
transformer做出的改良/改变
seq to seq 处理不了太长序列的原因是什么? 是梯度消失, 由于参与计算的数值大多是0-1之间,大于1则会梯度爆炸,小于0, 计算层多了,梯度就消失了,数据算着算着也没了,或固定不变 尽管有BN,层归一化等技巧,但效果仍不好, 终于,transformer来了... 将拼接改为 相加+ 数据流过多个层之后,变得小了,那么就加到原来的数据层上,让原来的数据产生微小的改变 数据每经过一次注意力计算,就产生一次微小的改变,这也叫短接,一条计算路径长,一条计算路径短 至于梯度,梯度以短路径的梯度为主,因为长路径的梯度消失了... 这就从根本上解决了梯度消失的问题,所以transformer可以设计到上千层... 缺点也有,因为每次计算改变量小,所以需要计算很多很多次...