ChatGPT 与 NLP 的发展历程
ChatGPT(Chat Generative Pre-training Transformer) 是一个 AI 模型,属于自然语言处理(Natural Language Processing ,NLP)领域,NLP 是人工智能的一个分支。所谓自然语言,就是人们日常生活中接触和使用的英语、汉语、德语等等。
基于规则的 NLP
基于规则的 NLP,是指使用人工编写的规则来处理自然语言。这些规则通常基于语法、语义和语用等方面的知识,可以用来解析和生成自然语言。
例如:
规则 1:当模型接收到用户的问句后,把问句中的“吗”字去掉,“?”换成“。”
规则 2:把“你”换成“我”,“我”字换成“你”
缺点:
1. 在自然语言中,任何规则都无法完全覆盖需求,因此在处理复杂的自然语言任务时效果不佳;
2. 规则无穷无尽,靠人力来完成将是一项天量的工作;
3. 本质上并没有把自然语言处理的任务交给计算机来完成,依然是人在主导。
基于统计的 NLP
基于统计的 NLP 则是利用机器学习算法**从大量的语料库中学习自然语言的规律特征**,在早期也被称为连接主义。它的重点在于,根据大规模原始语料学习一个语言模型,而这个模型并不直接学习如何解决具体的某种任务,而是学习从语法、词法、语用,到常识、知识等信息,把它们融汇在语言模型中。直观地讲,它更像是一个知识记忆器,而非运用知识解决实际问题。
基于统计的方法远远比基于规则的方法受欢迎,然而它最大的缺点是黑盒不确定性,即规则是隐形的,暗含在参数中。例如,ChatGPT 也会给出一些模棱两可、不知所云的结果,我们无从依照结果来判断模型为什么给出这样的答案。
基于强化学习的 NLP
ChatGPT 模型是基于统计的,然而它又利用了新的方法,带人工反馈的强化学习(Reinforcement Learning with Human Feedback,RLHF) ,以此取得了卓越的效果,把 NLP 的发展带入了一个新阶段。
基于统计的方式能够让模型以最大自由度去拟合训练数据集;而强化学习就是赋予模型更大的自由度,让模型能够自主学习,突破既定的数据集限制。
ChatGPT的发展路线
GPT 初代
GPT 的语言建模
语言模型的编解码
语言是一个显式存在的东西,但大脑是如何将语言进行理解、转化和存储的,则是一个目前仍未探明的东西。这个问题实际上表达了一个人脑运用语言的特点:人脑并不直接存储文字,而是将文字编码成某种神经元信号,再经过解码,形成想要表达的文字,表述出来。
**编解码**的概念广泛应用于各个领域,在 NLP 领域,模型操控语言一般包括三个步骤:
> 接受听到或读到的语言 -> 人的大脑理解 -> 输出要说的语言。
大脑理解语言这个过程,就是大脑将语言编码成一种可理解、可存储形式的过程,这个过程就叫做语言的编码(Encoder) 。相应地,把大脑中想要表达的内容,使用语言表达出来,就叫做语言的解码(Decoder)
GPT-2
GPT-2 主要就是在 GPT 初代的基础上,又添加了多个任务,比如机器翻译、问答、文本摘要等等,扩增了数据集和模型参数,又训练了一番。训练效果样例如下图所示,这是一些 GPT2 训练得到的结果,输入左边的问题,模型会给出第二列的答案。
GPT-3
大模型中的大模型
GPT-3 里的大模型计算量是 GPT-1 的上千倍。如此巨大的模型造就了 GPT-3 在许多十分困难的 NLP 任务,诸如撰写人类难以判别的文章,甚至在编程语言方面,编写 SQL 查询语句、React 或者 JavaScript 代码上都具有优异的表现。
对话模式
GPT 系列模型都是采用 decoder 解码器结构进行训练的,也就是更加适合文本生成的形式。即输入一句话,输出也是一句话。这被称之为对话模式。它非常像人类的沟通交流模式。
小样本(Few-Shot)学习
GPT3 就提出了小样本学习的概念,简单来讲,就是让模型学习语言时,不需要那么多的样例数据。
强化学习
训练 ChatGPT 所需要的文本,主要来自于互联网,这是一个有限的集合。而人类对 ChatGPT 提出的问题则无穷无尽,永远没有尽头,人类想要知道、感兴趣的内容,并不一定就存在互联网上。
而 ChatGPT 所利用的强化学习的思路,则是模拟一个**环境模型(Reward 模型)。 首先,ChatGPT 会针对某一个问题,生成一个回答,环境模型会对 ChatGPT 生成的答案做评价,评价一个分值出来(如 10 分、3 分等等,高分代表奖励,低分代表惩罚),而不具体给出标准答案。ChatGPT 接收到评价反馈后,可以根据这个数值做模型的进一步训练,朝着生成更加恰当答案的方向拟合。
而 ChatGPT 所利用的强化学习的思路,则是模拟一个**环境模型(Reward 模型)。 首先,ChatGPT 会针对某一个问题,生成一个回答,环境模型会对 ChatGPT 生成的答案做评价,评价一个分值出来(如 10 分、3 分等等,高分代表奖励,低分代表惩罚),而不具体给出标准答案。ChatGPT 接收到评价反馈后,可以根据这个数值做模型的进一步训练,朝着生成更加恰当答案的方向拟合。
语言模型
定义:**语言模型,就是由计算机来实现类似于人的语言交流、对话、叙述能力,它集中体现在模型能够依赖上下文进行正确的文字输出**。
ChatGPT 语言模型的数学建模
1、语言模型基础建模
最经典的语言建模就是根据上文,输出下文,也就是例 2 的形式,这也是 GPT 模型的建模形式。
语言模型的建模公式可以表示为:
P(w1,w2,...,wn)=P(w1)∗P(w2∣w1)∗P(w3∣w1,w2)∗...∗P(wn∣w1,w2,...,wn−1)P(w1,w2,...,wn)=P(w1)∗P(w2∣w1)∗P(w3∣w1,w2)∗...∗P(wn∣w1,w2,...,wn−1)
其中, w1,w2,...,wnw1,w2,...,wn表示一个句子中的字符序列,P(wi)P(wi)表示字符 wiwi在语料库中出现的概率, P(wi∣w1,w2,...,wn−1)P(wi∣w1,w2,...,wn−1)表示在已知前面字符的情况下,字符 wiwi 出现的概率,即依赖上文,对下文的预测**。把每一个字符都按照此方式预测出来,其结果就是整条语句的出现概率。
P(w15=网∣w0−14=掘金...交流)=P(w0−14=掘金...交流)P(w0−15=掘金...流网)=0.0000010.0000003=0.33
P(w16=站∣w0−15=掘金...流网)=P(w0−16=掘金...网站)P(w0−15=掘金...流网)=0.00000020.0000003=0.67P(w16=站∣w0−15=掘金...流网)=P(w0−15=掘金...流网)P(w0−16=掘金...网站)=0.00000030.0000002=0.67
2、N-gram 语言建模
通常情况下,语言模型的建模公式采用n-gram 模型,这个词没有对应的中文翻译,其含义是就近原则,距离第 i 个字符相隔 n 个字符距离以上的,就不在考虑范围内了。公式来讲,就是将条件概率 P(wi∣w1,w2,...,wi−1)P(wi∣w1,w2,...,wi−1) 近似为 P(wi∣wi−n+1,wi−n+2,...,wi−1)P(wi∣wi−n+1,wi−n+2,...,wi−1),其中 n 为 n-gram 模型中的 n 值。这样可以简化模型的计算,并且在一定程度上保持模型的准确性。
P(w15=网∣w7−14=便捷...交流)=P(w7−14=便捷...交流)P(w7−15=便捷...流网)=0.00010.00003=0.33
P(w16=站∣w8−15=捷的...流网)=P(w8−16=捷的...网站)P(w8−15=掘金...流网)=0.000020.00003=0.67P(w16=站∣w8−15=捷的...流网)=P(w8−15=掘金...流网)P(w8−16=捷的...网站)=0.000030.00002=0.67
3、语言模型 log 化
我们再来观察一下这个语言模型公式:
P(w1,w2,...,wn)=P(w1)∗P(w2∣w1)∗P(w3∣w1,w2)∗...∗P(wn∣w1,w2,...,wn−1)P(w1,w2,...,wn)=P(w1)∗P(w2∣w1)∗P(w3∣w1,w2)∗...∗P(wn∣w1,w2,...,wn−1)
这个式子是一个连乘,其中每一个因子都是一个概率值,介于 0~1 之间。多个这样的数值相乘,其乘积会越来越小,趋近于 0。所以我们应当对上述式子做对数变换:
log(P(w1,w2,...,wn))=log(P(w1))+log(P(w2∣w1))+log(P(w3∣w1,w2)) +...+log(P(wn∣w1,w2,...,wn−1))log(P(w1,w2,...,wn))=log(P(w1))+log(P(w2∣w1))+log(P(w3∣w1,w2)) +...+log(P(wn∣w1,w2,...,wn−1))
1、ChatGPT 的建模公式
ChatGPT 是利用成千上万的文本语料训练得来的。每一篇语料都是一条文本,可以抽象成w1,w2,...,wnw1,w2,...,wn这样的一串字符序列,假设这个大的语料为 U,则我们的建模公式又可以表示成:
log(P(U))=∑ilog(P(wi∣wi−k,wi−k+1,...,wi−1))log(P(U))=∑ilog(P(wi∣wi−k,wi−k+1,...,wi−1))
当然,ChatGPT 模型是由巨量的参数构成的,设ΘΘ为 ChatGPT 的参数集合,则模型的建模公式可以表示成:
log(P(U))=∑ilog(P(wi∣wi−k,wi−k+1,...,wi−1;Θ))log(P(U))=∑ilog(P(wi∣wi−k,wi−k+1,...,wi−1;Θ))
2、语言模型中的最大似然概率
在 ChatGPT 的语言模型公式中,左半边是log(P(w1,w2,...,wn))log(P(w1,w2,...,wn)),它其实就是一种最大似然的建模方式。在概率论中,最大似然概率是一种最为简单,也最为广泛应用的近似估计方法。
3、ChatGPT 语言模型的训练方式
模型的训练方式,归根结底就是要做概率的预测。
chatGPT与自然文字之间的转换
这种转换包括两个步骤,Tokenizer 和 Embedding。本节主要介绍这两个模块。
Tokenizer
token 是任何 NLP 神经网络 模型接收用户输入的最小粒度。token 本身就是一些字符的组合,如英文单词`#cat`、中文词汇`鞋子`、英文词缀`ly`、中文汉字`珂`等,都可以看作是一个 token。
kenizer 算法 BPE 执行流程
Tokenizer 目前最流行的实现方法是 字符对编码BPE(Byte Pair Encoding) 算法,它也是 ChatGPT 采用的算法。BPE 算法是根据一份 token 词表(Vocabulary),将输入的文本拆解成若干个 token。其中,每一个 token 都存在于词表。
ChatGPT 模型在回答用户问题,输出答案时,也是首先输出 token 序列,再将 token 序列反转为正常的自然语言文本,这个操作叫做 De-tokenization。它与 Tokenization 是完全**互逆**的操作。读者可以尝试把上面的 token 序列合并成完整的文本句子。
Byte-level BPE 算法
之前介绍的 BPE 算法是基于字符的,除此之外,还有一种基于字节的 BPE 算法(Byte-level BPE)。这种方法,主要是为了克服基于字符的 token 词表,由于各种特殊字符数量太庞大导致效果变差。
这种算法的执行步骤和上述的 BPE 算法完全一致,唯一的区别在于,BPE 算法直接操作 Unicode 字符,而 Byte-level BPE 算法把文本的字节作为直接操作的对象。
Tokenizer 的好处
克服长尾效应 OOV
在英文单词中,最常出现的 5000 个单词占据了实际使用量的 90%。而那些极低频的单词数量极多,但总共加起来的实际使用量也不超过 2%。这就是自然语言的长尾效应,这种现象也出现在其它语言中。
直接把极低频的单词和字符当作 token,本身意味着数据量的缺乏,会导致它有可能不在词表中(Out Of Vocabulary,OOV),对 NLP 模型的性能产生很大的影响。因此,引入 Tokenizer,采用 BPE 算法可以避免低频词作为 token。
例如,根据上述训练例子得到的词表,`#strangest` 这个词在训练语料中词频较低,可能不出现在 token 词表中,但 “`#strang`” 和 “`est`” 一定以较高的频率出现在 token 词表中。
多语言支持
在早期,NLP 神经网络模型功能十分单一,且仅支持某一种语言。一个针对英文的文本分类模型,并不能支持中文的文本分类。而 BPE 算法,包括 Byte-level BPE 算法的设计,使得一份词表中包含了多种语言的字符,支持模型的多语言处理功能。
词嵌入(Embedding)
ChatGPT 的输入文字转换为 token 之后,还需要将 token 再转换为张量,这个过程叫做词嵌入( Embedding),同时 embedding 也指被转换后得到的张量本身。
在神经网络中,张量(Tensor)是指多维数组,它可以存储和处理大量的数据,是神经网络中最基本的数据结构。张量一般都以浮点数(小数的一种计算机表示形式)作为元素进行填充。
例如,a=[[1.034,0.932,−0.347],[0.023,−1.025,0.256]]a=[[1.034,0.932,−0.347],[0.023,−1.025,0.256]]就是一个(2,3)形状的张量,是一个多维数组。
而向量(vector),就是高中数学中的概念,一般就可以看作是一维张量。
ChatGPT 从功能上看,是一个语言模型,但从结构上看,它是一个多层的、复杂的神经网络模型,每一层的神经网络都在进行浮点数张量(Tensor)的数字计算,而 ChatGPT 的输入是文字符号,token 也是文字符号。因此,token 需要先转换为浮点数字,再进入模型中进行计算。将用户输入的 token 转换为浮点数张量的过程,就叫做词嵌入(Embedding)。当模型将结果计算完,也要将最终的浮点数转换为具体的 token,作为输出。
在自然语言中,文字的顺序是非常重要的,“我喜欢你”,和 “你喜欢我” 表达的含义是完全不同的。所以,ChatGPT 考虑到模型的每个 token 相互之间的顺序不能改变,需要明确地在输入端标识出每个 token 的位置张量(Position Embedding),其大小和 token 的 embedding 是一致的。两者以如下形式融合起来: embeddinginput = UWe + Wpembeddinginput = UWe + Wp 。
假设 token 数量小于模型可接收的最大数量,那么,上述公式可以退化为: embeddinginput = We + Wpembeddinginput = We + Wp。
上图中做了假设:Q1、A1、Q2 分别包含了 4 个 token。当然,在实际输入中,每个 segment 包含的 token 数都是可以灵活变化的;上面对话的轮数仅有两轮,而实际输入中,对话轮数可以非常多,形如 Q1、A1、Q2、A2、...、Qn, 只要所有 segment 对应的 token 总数加起来不超过模型允许的最大 token 数即可。
因此,输入给 ChatGPT 的 embedding可以表示为如下公式:
embedding = embeddingsegment + embeddingposition + embeddingtokenembedding = embeddingsegment + embeddingposition + embeddingtoken
mbedding 的好处
最早的时候,NLP 是直接处理文本字符串,没有 Embedding 这个操作的。Embedding 这个操作最早是由 word2vec 模型提出并实施的,GPT系列模型,包括 ChatGPT 已将此操作作为了固定默认步骤。
Embedding 方便接入大规模神经网络
我们在第 2 节中论述了,AI 想要有较高水平的智能,其模型规模必然比较大,参数量众多。在机器学习领域,神经网络模型是最容易扩展其模型规模的。我们会在第 8 节讲解神经网络相关的概念。
如果没有 Embedding 操作,那么 NLP 领域依然停留在直接处理字符的层面上,模型的规模扩展难度较大。embedding 将文字对应的 token 转换为抽象的固定维度的张量,标志着 NLP 迈入了深度神经网络的大门。
Embedding 抽象了 token 的语义
当我们训练好 ChatGPT 这个模型之后,假设我们抽取出如下 token 对应的 embedding 向量:
#price(价格),#cost(开销),#trunk(卡车),#texi(出租车)
其对应的均为 M 维 embedding 向量。计算两个向量相似度的方式主要采用余弦距离,则一定有:
cos(price,cost) > cos(price,truck)cos(price,cost) > cos(price,truck)
cos(trunk,texi) > cos(cost,texi)cos(trunk,texi) > cos(cost,texi)
其含义为,price 和 cost 在 embedding 上的相似度,要大于 price 和 truck 的相似度,这符合人们的语言直觉。可以得出结论,在自然语言中,语义相近的两个词汇,其 embedding 向量之间的数学意义上的距离更相近。