从图灵的模仿游戏到香农的熵,从一个神经元到千亿参数的 Transformer。一个只会预测下一个词的程序,何以通向智能? 遍览诗书亿万行,唯将下字细思量。云山千里文中见,可识秋风一夜凉? 这篇文章想用一条线,讲清楚 ChatGPT 这类大语言模型是怎么回事:它在做什么、为什么能做到、怎么做到的、做不好什么。不需要机器学习背景。用到的数学只有加减乘除和对数,对数也会从“折半了几次”讲起。全文的例子尽量来自同一个猜数字游戏和同一句“他口渴了,于是喝了一杯____”,看懂一个例子,后面会一路用到。 全文近 3 万字,完整读完大约需要 1.5 小时,可以分两次读:前三章讲原理,最后一章讲从模型到产品。带计算过程的代码块和公式,跳过也不影响理解,只看加粗的结论就能读通。想真正弄懂的话,建议拿笔跟着算一遍,每个数字都能核对。 全文大致沿着一串问题往下走,很多小节的结尾会抛出一个问题,由后面的内容来回答。读不下去的时候,回头找找前面留下的问题,就能找回主线。只关心怎么用、有什么局限的读者,可以先读「语言模型的本质」的前两节,再直接跳到最后一章「从模型到 ChatGPT」。最后的「总结」用十几行把全文串了起来,读完可以回头对照一下;末尾还留了几个问题供思考。 **语言模型的本质** 小龙在之前的年会上给大家分享过一段话:“信息就是惊喜,就是你猜不到的程度。信息量是由内容的离谱程度来决定的,越离谱信息量就越高。”这句话中暗含了语言模型的本质原理。 **预测下一个 token** 在解释之前,我们先玩一个词语接龙游戏,请补全: 床前明月____ 所有人几乎都会填“光”,那再来看: 今天天气很____ 这次答案不唯一:好、热、冷、不错……但也不是毫无规律,很少有人会填一个跟天气八竿子打不着的词,比如“今天天气很贵”。如果把各种可能按把握大小写下来,大概是这样(示意): | 候选 | 概率(示意) | | --- | --- | | 好 | 35% | | 热 | 20% | | 冷 | 15% | | 不错 | 10% | | 其他所有候选合计 | 20% | 如果把这道题交给语言模型来做,它给出的也是这样一张表。注意表里的“不错”是两个字,却和“好”一样算作一个候选。这是因为语言模型处理文字的最小单位不是“字”,而是 token。一个 token 可能是一个字,也可能是由多个字组成的一个词。以“今天天气很好”为例,模型看到的可能是这样: 今天 | 天气 | 很 | 好 这 6 个字被切成了 4 个 token:“今天”“天气”各占一个 token,“很”“好”各自单独成一个 token。所以模型“接龙”时,每一步补上的是一个 token,而不一定是一个字。 之所以要合并,一是省步数:模型每生成一个 token 都要完整算一遍,合并后“今天天气很好”只需算 4 步而不是 6 步。二是常一起出现的字本来就该当作整体,比如“今”后面经常跟着“天”,合成一个 token 后模型就不用反复去猜这种显而易见的搭配。 现在回到上面那张概率表,它就是语言模型做的事: 语言模型,是一个给定前文、输出“下一个 token 概率分布”的程序。 模型每次只预测一个 token,那一整段话是怎么写出来的?做法很简单:从概率分布里选出一个 token 接到前文后面,再把新的前文交给模型预测下一个,如此循环(示意): 今天天气很 → 好 今天天气很好 → , 今天天气很好, → 适合 今天天气很好,适合 → 出门 **为什么预测 token 能带来智能** “预测下一个 token”听起来像高级版的输入法联想,它凭什么和“智能”扯上关系? 1950 年,图灵在论文《计算机器与智能》里讨论“机器能思考吗?”。他觉得“思考”太难定义,于是换了个问法,设计了一个“模仿游戏”,也就是后来所说的图灵测试: 1. 一位裁判通过打字,和两个看不见的对象聊天; 2. 其中一个是人,另一个是机器; 3. 裁判可以问任何问题,聊完后判断哪个是人、哪个是机器。 如果裁判反复测试,也没法可靠地分辨出谁是机器,那就可以认为这台机器具备了人的智能。 分不清机器写的文字和人写的文字,就可以认为机器有了人的智能。 注意,这个测试里裁判能看到的只有文字。机器用什么做的、内部怎么运转,都不重要,重要的是它写出来的东西像不像人写的。 再看语言模型做的事:它从海量人类文字中学习“给定前文,人接下来会写什么”。学得越准,它一个 token 一个 token 接出来的文字就越像人写的。如果它预测的概率分布和人写作时的分布完全一致,那它写出的文字和人写的就没有区别,裁判怎么看也分不出来。 所以,把预测下一个 token 做到极致,就是在通过图灵测试。 而要预测得准,光记住字词搭配是不够的。看几个例子: - 法国的首都是____ 要填“巴黎”,得有知识。 - 小明比小红高,小红比小刚高,三个人里最矮的是____ 要填“小刚”,得会推理。 - 他打开冰箱,发现牛奶已经过期了,于是皱着眉头把它____ 要填“倒掉”或“扔了”,得懂常识和人的行为。 人写下的文字里,藏着知识、逻辑、常识和情感。要把人接下来会写的 token 猜准,模型就不得不把这些东西学进去。“预测”这个看似简单的目标,逼着模型去掌握文字背后的东西。 当然,“分辨不出”只是图灵给出的一个行为标准,机器是否真的“理解”,至今仍有争论。但它给了我们一个清晰、可操作的目标:让模型预测的概率尽量接近人。 那“接近”该怎么衡量?预测得准不准,能用什么数字来表示?这就要从概率和信息的关系说起。 **概率对应了多少的信息?** 我从 1~8 中等概率地选一个整数,不告诉你。你可以问问题,但我只能回答“是”或“否”。 你当然可以挨个问: 是 1 吗?不是。 是 2 吗?不是。 是 3 吗?不是。 …… 但这种问法容易浪费机会:每次得到“不是”,只排除一个数字。 更好的方式是,每次用一个问题把剩余候选分成数量相等的两组。假设我选的是 6: | 第几问 | 你的问题 | 我的回答 | 剩余候选 | | --- | --- | --- | --- | | 开始 | — | — | 1、2、3、4、5、6、7、8 | | 第一问 | 大于 4 吗? | 是 | 5、6、7、8 | | 第二问 | 大于 6 吗? | 否 | 5、6 | | 第三问 | 大于 5 吗? | 是 | 6 | 三个问题,确定答案。 这不是因为你碰巧猜中了 6,而是因为这种问法能够让任何一个答案都在三次问答后被确定。 每得到一次回答,你都排除了一半候选: 8 个候选 → 4 个候选 → 2 个候选 → 1 个答案 信息,就是帮助你消除不确定性的东西。 在这个等概率游戏里,每次折半的回答提供 1 bit 信息,三次一共 3 bit。不要把 bit 想得太神秘,这里可以把它理解为:区分两个等概率可能性所需要的信息量。 再换几个范围试试: - 从 4 个等概率数字中确定一个,需要折半 2 次。 - 从 8 个等概率数字中确定一个,需要折半 3 次。 - 从 16 个等概率数字中确定一个,需要折半 4 次。 候选越多,起初越不确定;要找到答案,需要获得的信息也越多。 顺带说一句:折半问法的好,不只是“最多三次”肯定能问出来,还在于它在平均意义上也是最省问题的。原因很直接:每次“是/否”回答最多只带来 1 bit 信息,而确定 8 个等可能候选中的一个至少需要 log₂8=3 bit,所以任何问法平均都至少要问 3 次。折半问法每次都把候选对半分、每次都拿满 1 bit,平均下来正好 3 次,刚好踩在这个下限上。 到这里,就可以把“概率”和“信息量”直接对上号。 单个结果的信息量是: I(x)=log_{1/2} p(x) 为什么底数是 1/2?因为信息量本质上就是“折半了多少次”。概率为 1/2 的结果,相当于在一半的可能里确定它,折半 1 次,对应 1 bit;概率为 1/8 的结果,要在八分之一的可能里确定它,折半 3 次,对应 3 bit。log_{1/2} 正好把这个“折半次数”数出来:概率每缩小一半,对数就加 1。 你只需要记住三点: - p(x) 是结果出现的概率。 - 概率越小,结果出现时带来的信息量越大。 - 如果一个结果本来就百分之百确定(概率为 1),知道它发生并不会带来新信息,信息量为 0。 第二点,就是开头小龙那句话:“信息就是惊喜,就是你猜不到的程度……越离谱信息量就越高。”越离谱,就是概率越小;概率越小,信息量越大。 听到“明天太阳从东边升起”,你毫无惊喜,因为它的概率接近 1,信息量接近 0;听到“明天太阳从西边升起”,那才是天大的新闻。 不过一般书面上更常见的写法,是把它写成负的以 2 为底。这两种写法其实是同一个式子(后面都采用这种写法): I(x)=-log₂ p(x) **熵:平均而言,答案有多难确定?** 现在改变规则:我选 1 的概率是 90%,剩下 10% 的概率分给 2~8。 这时,“大于 4 吗”未必还是最有效的第一问。你可以先问: 是 1 吗? 90% 的时候,一问就结束了。 这说明,难度不只由“有几个候选”决定,还与各个候选出现的概率有关。同样是 8 个数字: - 如果每个数字都一样可能,你很难提前判断。 - 如果几乎每次都是 1,你已经知道很多,剩余的不确定性就小。 要描述游戏的平均难度,就得把每种结果的信息量,按照出现概率加权平均。这个平均值就是熵,它衡量的是这种平均不确定性。 H(X)=Σ_x p(x)I(x)=-Σ_x p(x)log₂ p(x) 用硬币对比一下: | 硬币的情况 | 熵 | 为什么 | | --- | --- | --- | | 正反各 50% | 1 bit | 两种结果同样可能,不好提前判断 | | 正面 90%,反面 10% | 约 0.469 bit | 大部分时候可以预期是正面 | | 必定正面 | 0 bit | 没有不确定性 | 第二行是这样算的: 正面:概率 0.9,信息量 −log₂0.9 ≈ 0.152 bit 反面:概率 0.1,信息量 −log₂0.1 ≈ 3.322 bit 熵 = 0.9 × 0.152 + 0.1 × 3.322 ≈ 0.137 + 0.332 ≈ 0.469 bit 罕见的反面信息量很大(3.3 bit),但它只占 10%,拉不高平均值。 把正面概率从 0 连续变到 1,就能看到熵的整体形状:正反各半时最不确定(1 bit),越偏向某一面,熵越低,到必定正面或必定反面时降为 0。 回到猜数字游戏,用同样的方法算一下两种规则下的熵。 1~8 等概率:每个数字的概率都是 1/8。 每个数字:概率 1/8,信息量 −log₂(1/8) = 3 bit 熵 = 8 × (1/8 × 3) = 3 bit 正好对应折半问法需要的 3 个问题。 1 的概率为 90%:剩下的 10% 平分给 2~8,每个数字的概率是 0.1 / 7 = 1/70 ≈ 0.0143。 数字 1:概率 0.9,信息量 −log₂0.9 ≈ 0.152 bit 数字 2~8:每个概率 1/70,信息量 −log₂(1/70) ≈ 6.129 bit 熵 = 0.9 × 0.152 + 7 × (1/70 × 6.129) ≈ 0.137 + 0.613 ≈ 0.750 bit | 猜数字的情况 | 熵 | | --- | --- | | 1~8 等概率 | 3 bit | | 1 占 90%,2~8 平分 10% | 约 0.750 bit | 同样是 8 个候选,概率一旦集中到 1 上,平均不确定性就从 3 bit 降到约 0.75 bit,只剩原来的四分之一左右。 熵不只是一个“难度分数”,它还有一个很实在的含义:平均最少要用多少 bit 才能把答案记下来,也就是数据能被压缩到的极限,任何无损编码的平均长度都不可能低于熵。 规律掌握得越准,编码就越短;能压到熵,说明数据里所有能被利用的规律都已经挖出来了,剩下的只是真正无法预测的随机性。 语言也是一样。下一个 token 的真实概率里,藏着语法、常识、逻辑和人的意图。模型预测得越准,就越能把文字压缩到接近它的熵;而要做到这一点,就不得不把文字背后这些深层的规律学进去。这就是「压缩即智能」的核心思路: 能把数据压缩得越短,说明对数据背后规律的掌握越深。 这和前面的图灵测试,是同一件事的两面: - 图灵测试给出的是标准:预测得和人一样,就可以认为有了人的智能。 - 压缩即智能给出的是原因:要预测得和人一样,就得把文字压缩到接近它的熵;而要压得这么短,最有效的办法就是学会文字背后的规律。 不过要注意,“预测越准、压缩越短”是数学事实;“压缩得好就是智能”只是一个有启发的研究视角,而不是已被证明的定理。比如“一万个 A”可以写成“A 重复一万次”,一个简单程序就能压得极短,但不能因此说它会推理。 为什么“压得短”意味着“学到了规律”,而不是把文字死记硬背下来?这个问题留到后面「背答案还是学方法」一节再细说。 那么,如果模型对概率的估计不准,编码会比熵多花多少? **交叉熵** 先说清楚一点:熵是数据本身的性质。只要我选数字的规则不变,熵就一直是 0.75 bit,模型估计得准不准都改变不了它。会变的是:按模型的估计去编码时,实际要花多少 bit。 假设真实规则还是“1 占 90%,2~8 平分 10%”,但模型以为 8 个数字等概率。用 p(x) 表示真实概率,q(x) 表示模型认为的概率。模型会按自己的判断安排编码:认为谁常见,就给谁短编码,结果 x 的码长就是模型眼中的信息量 -log₂ q(x)。 模型认为每个数字都是 1/8,于是给每个数字都分配 3 bit。可实际上 90% 的时候出现的都是 1,本来 0.152 bit 就够了,却每次都花了 3 bit: 数字 1:真实出现 90%,模型给的码长 −log₂(1/8) = 3 bit 数字 2~8:真实一共出现 10%,模型给的码长也都是 3 bit 平均码长 = 0.9 × 3 + 0.1 × 3 = 3 bit 比熵多花了 2.25 bit,这些都是估计错了概率而白白浪费的。 把这个算法写成公式,就是交叉熵: H(p,q)=-Σ_x p(x)log₂ q(x) 和熵的公式相比,只是把对数里的 p(x) 换成了 q(x): - p(x)(真实概率)负责加权:这个结果实际多常出现。 - q(x)(模型概率)负责定价:这个结果每出现一次要花多少 bit。 当模型的估计和真实完全一样(

打开网易新闻 查看精彩图片