ARTICLE · INTELLIGENCE

战地情报 · 详情页

来自尧图项目组的一线实战观察与深度解析

从N-gram到GPT:大语言模型入门基础知识与核心原理梳理

从N-gram到GPT:大语言模型入门基础知识与核心原理梳理

简介:这份PDF资料面向大语言模型零基础学习者与希望系统梳理概念的开发者,围绕语言模型这一核心主题,帮助读者建立从统计语言模型到预训练大模型的完整认知框架。内容涵盖大语言模型背景、语言模型定义与评估指标,并梳理语言模型发展的四个阶段:基于规则和统计的模型、神经语言模型、预训练语言模型以及大语言模型,同时深入讲解N-gram语言模型的马尔科夫假设、bigram与trigram概率计算、数据稀疏与OOV等典型问题,以及神经网络语言模型的词向量输入、全连接层与softmax输出结构。资源包共1个PDF文件,大小约3.24MB,结构清晰、便于按章节阅读。目前已有129人学习,适合作为入门阶段的概念扫盲与知识索引材料,帮助读者快速理解LLM的基本原理、技术演进脉络与关键术语,为后续深入学习Transformer、GPT等模型打下基础。

1. 从 N-gram 到 GPT:一份 LLM 入门知识包到底能帮你解决什么

很多人第一次接触大语言模型,是从调 API 或者跑一个开源权重开始的,结果卡在“为什么模型能预测下一个词”这种最底层的问题上。这份《大语言模型入门的基础知识》资源包,核心就是补上这段断层:它从语言模型的概率定义讲起,沿着 N-gram、神经网络语言模型、Transformer 预训练模型一路推到大语言模型,把 LLM 的来龙去脉拆成可验证的知识点。适合两类人:一是刚转方向、需要把术语和演进脉络理清的开发者;二是已经会调模型、但被面试或技术评审追问“N-gram 的马尔科夫假设到底解决了什么”时答不上来的从业者。它不教你怎么训练一个千亿模型,但能让你在讨论 LLM 时不再只停留在“参数量大”这个层面。

2. 语言模型的定义与概率计算:从链式法则到 N-gram 的工程取舍

2.1 语言模型到底在算什么

资源里给了一个很朴素的定义:语言模型就是计算一个词序列 ( S = {W_1, W_2, \dots, W_n} ) 发生概率 ( P(S) ) 的模型。如果序列符合语用习惯,给高概率;否则给低概率。这个定义看起来简单,但它直接决定了后面所有模型的设计目标。

最原始的计数法是这样的:假设数据集有 ( N ) 个句子,统计目标句子出现次数 ( n ),则 ( P(S) = n / N )。这个做法在工程上几乎不可用,因为一旦句子没在训练集里出现过,概率直接归零。这就是数据稀疏问题最直观的体现。

链式法则把 ( P(S) ) 拆成条件概率连乘:

[ P(W_1, W_2, \dots, W_n) = \prod_{i=1}^{n} P(W_i \mid W_1, \dots, W_{i-1}) ]

理论上没问题,但参数空间随序列长度指数增长,根本估不完。所以 N-gram 引入马尔科夫假设:当前词只与前面有限个词有关。

2.2 N-gram 的阶数与参数计算

资源里把 N-gram 的阶数讲得很清楚:

模型类型假设常见用途
unigram词与周围词独立极简基线
bigram当前词只依赖前 1 个词实践常用
trigram当前词只依赖前 2 个词实践常用

以 bigram 为例,参数计算就是数数:

# 假设语料已经分好词,sentences 是 list[list[str]] from collections import Counter sentences = [ ["我", "想", "去", "打", "篮球"], ["我", "想", "吃", "晚饭"], ["你", "想", "去", "哪里"], ] bigram_count = Counter() unigram_count = Counter() for sent in sentences: for i, word in enumerate(sent): unigram_count[word] += 1 if i > 0: bigram_count[(sent[i-1], word)] += 1 # 计算 P(想|我) p_xiang_given_wo = bigram_count[("我", "想")] / unigram_count["我"] print(p_xiang_given_wo) # 输出约 0.67(取决于语料)

这段代码的逻辑很直接:bigram_count统计相邻词对出现次数,unigram_count统计单个词出现次数,两者相除得到条件概率。参数说明上,sentences是分词后的语料,实际工程中需要先做分词和特殊符号处理。资源里给出的例子是 ( P(\text{想}|\text{我}) = 0.38 ),具体数值取决于语料规模,但计算方式一致。

有了 bigram 参数后,计算整个句子概率就是连乘:

def bigram_sentence_prob(sent, bigram_count, unigram_count): prob = 1.0 for i in range(1, len(sent)): pair = (sent[i-1], sent[i]) # 加一平滑,避免零概率 prob *= (bigram_count[pair] + 1) / (unigram_count[sent[i-1]] + len(unigram_count)) return prob # 预测下一个词:我想去打【mask】 candidates = ["篮球", "晚饭"] for c in candidates: sent = ["我", "想", "去", "打", c] print(c, bigram_sentence_prob(sent, bigram_count, unigram_count))

这里加了最简单的加一平滑,否则只要有一个词对没出现,整个句子概率就是 0。资源里也点出了 N-gram 的优缺点:参数易训练、可解释性强,但只能建模前 n-1 个词,n 增大后参数空间指数增长,OOV 和数据稀疏问题始终存在。

提示:实际工程中 bigram 和 trigram 用得最多,再往上参数爆炸的代价往往换不来等比例的收益。

3. 从神经网络到 Transformer:预训练范式怎么把语言模型推到大模型阶段

3.1 神经网络语言模型的结构与改进

N-gram 的硬伤是泛化差,神经网络语言模型换了个思路:不再数词对,而是学词向量和概率分布。资源里描述的结构是:

  • 输入层:前 n-1 个词的词向量 ( C(w_{t-n+1}), \dots, C(w_{t-1}) ),首尾拼接成 ( (n-1) \times m ) 的向量 ( x )
  • 隐藏层:全连接 + tanh 激活
  • 输出层:V 个节点(V 是词表大小),接 softmax 得到下一个词的概率分布

用代码表示这个前向过程大致是:

import numpy as np def neural_lm_forward(context_words, C, W1, b1, W2, b2): """ context_words: 前 n-1 个词的索引列表 C: 词向量矩阵,shape (V, m) W1, b1: 隐藏层参数 W2, b2: 输出层参数 """ # 第一层:拼接词向量 x = np.concatenate([C[w] for w in context_words]) # shape (n-1)*m # 第二层:全连接 + tanh h = np.tanh(W1 @ x + b1) # 第三层:输出 logits,再 softmax logits = W2 @ h + b2 exp_logits = np.exp(logits - np.max(logits)) # 数值稳定 probs = exp_logits / np.sum(exp_logits) return probs # 每个词的概率

参数说明:C是词向量矩阵,维度 ( V \times m ),( m ) 是词向量维度;W1和b1是隐藏层参数;W2和b2是输出层参数。相比 N-gram,这个结构通过词向量共享统计强度,缓解了数据稀疏,但资源也指出它对长序列建模能力有限,可能出现梯度消失。

3.2 Transformer 预训练与微调范式的落地逻辑

资源把基于 Transformer 的预训练语言模型单独列为一个阶段,代表是 GPT、BERT、T5。核心变化是:不再只做“预测下一个词”,而是先在大规模通用文本上预训练,学到通用语言表示,再在具体下游任务上微调。

预训练阶段常见的目标有两种:

  • 自回归(GPT 系):根据前文预测下一个词
  • 自编码(BERT 系):掩码语言模型,预测被 mask 的词

微调阶段就是把预训练好的权重加载进来,换一个任务头,用少量标注数据更新参数。资源里总结的优缺点很到位:泛化能力强、语义表示丰富、防过拟合,但计算资源需求大、可解释性差。

3.3 大语言模型阶段的参数规模与能力跃迁

资源里给了一个关键节点:2020 年 GPT-3 参数量 1750 亿,首次展示了大语言模型的性能。和 BERT、GPT-2 不同,GPT-3 可以在不调整权重的情况下,仅依据用户给出的任务示例完成具体任务,也就是少样本/零样本推理。

这个阶段的特点资源里列得很清楚:

维度预训练语言模型大语言模型
参数量亿级到十亿级千亿级及以上
使用方式微调为主提示/示例为主
能力特定任务对话、生成、多模态
对齐较少强调强调可靠、安全、无毒

从工程视角看,这个跃迁意味着两件事:一是普通开发者很难从头训练,二是应用重心从“训模型”转向“用模型”。资源里提到的 GPT-3、ChatGPT、GLM、BLOOM、LLaMA 等,都是这个阶段的代表。

4. 评估指标与常见误用:语言模型到底该怎么量化和对比

4.1 困惑度(Perplexity)的计算与解读

语言模型最常用的自动指标是困惑度,本质是交叉熵的指数形式。对于测试集 ( W = w_1, w_2, \dots, w_N ):

[ PPL = \exp\left( -\frac{1}{N} \sum_{i=1}^{N} \log P(w_i \mid w_1, \dots, w_{i-1}) \right) ]

用代码算就是:

import math def perplexity(log_probs): """ log_probs: 每个词的对数概率列表 """ avg_neg_log = -sum(log_probs) / len(log_probs) return math.exp(avg_neg_log) # 示例:模型对 5 个词的对数概率 log_probs = [-0.5, -1.2, -0.8, -1.5, -0.3] print(perplexity(log_probs)) # 输出约 2.36

参数说明:log_probs是模型对每个真实词给出的对数概率,越低说明模型越“惊讶”,PPL 越高。PPL 越低越好,但要注意不同词表、不同分词方式下的 PPL 不可直接比较。

4.2 评估指标在 LLM 时代的局限

资源里把评估指标放在最后一部分,但实际工程中这里坑最多。PPL 对生成任务只能反映“像不像人话”,不能反映事实正确性、逻辑一致性、安全性。大语言模型阶段更常用的是人工评估、任务准确率、对齐指标等。

注意:拿 PPL 去对比两个不同 tokenizer 的模型,结论基本无效。这是最常见的误用之一。

5. 避坑与排查:入门 LLM 时最容易翻车的五个地方

5.1 把 N-gram 的概率计算直接套到长句上

现象:用 bigram 算一个 20 词句子的概率,结果几乎全是 0。 原因:数据稀疏,长句里只要有一个词对没出现,连乘就归零。 解决:加平滑(加一、Kneser-Ney 等),或者改用神经网络语言模型。实际工程中 bigram/trigram 只适合短窗口建模。

5.2 混淆“语言模型”和“大语言模型”的评估方式

现象:用 PPL 去评估一个对话模型的回复质量,发现 PPL 很低但回答很离谱。 原因:PPL 衡量的是对真实词序列的拟合程度,不是生成质量。 解决:生成任务用任务指标 + 人工评估,PPL 只作为训练过程中的参考。

5.3 忽略 tokenizer 对概率和指标的影响

现象:两个模型 PPL 差很多,但实际效果差不多。 原因:分词方式不同,词表大小不同,PPL 不可直接比较。 解决:对比模型时统一 tokenizer,或者改用 bits-per-character 等与分词无关的指标。

5.4 以为参数量大就一定好

现象:选了一个参数量更大的模型,推理成本翻倍,效果提升却不明显。 原因:参数量只是能力的一个维度,训练数据质量、对齐方式、推理配置都影响最终表现。 解决:先明确任务类型,再在参数量、延迟、成本之间做权衡。资源里也提到大语言模型“算力要求高、训练时间长”,落地时要算清楚账。

5.5 忽视预训练和微调的数据泄漏

现象:微调后测试集准确率异常高,上线后效果暴跌。 原因:微调数据里混入了测试集样本,或者预训练语料里已经包含了下游任务数据。 解决:严格划分训练/验证/测试集,检查预训练语料和下游数据的重叠。这个坑在 LLM 时代更隐蔽,因为预训练语料规模太大,很难完全排查。

6. 把这份知识包用起来:一条从概念到动手的验证路径

资源本身是知识梳理型,不是代码包,所以最好的用法是“边读边验证”。我一般会按下面这条路径走一遍,基本能把 LLM 入门阶段的核心概念串起来。

第一步,用 Python 实现一个 bigram 语言模型,语料不用大,几百句就够。重点不是效果,而是亲手感受数据稀疏和 OOV 是怎么发生的。代码就是第 2 章里那段,加上平滑后跑几个句子,看看概率怎么变。

第二步,用一个小型神经网络语言模型复现第 3 章的前向过程。不需要训练到收敛,随机初始化权重,跑一次前向,确认输出维度是词表大小、softmax 后和为 1。这一步能帮你理解“词向量 + 全连接 + softmax”到底在算什么。

第三步,找一个开源的小型预训练模型(资源里提到的 LLaMA 系列有较小参数版本),加载 tokenizer,算一个句子的 PPL。然后换一个不同 tokenizer 的模型再算一次,亲自验证“PPL 不可直接比较”这个结论。

第四步,把资源里那张语言模型发展阶段表默写一遍:基于规则和统计、神经网络、预训练、大语言模型,每个阶段写一个代表模型和一个核心问题。能默写出来,说明脉络清楚了。

阶段代表核心问题
规则和统计N-gram数据稀疏、泛化差
神经网络NNLM长序列建模弱
预训练BERT、GPT计算资源大
大语言模型GPT-3、LLaMA算力、对齐、安全

最后一步,拿资源里的思考题自测:什么是大语言模型?语言模型的主要类别是什么?常用的 N-gram 语言模型是什么?如果能不看资料答出来,这份知识包就算吃透了。

从那以后我每次带新人,都强制让他们先手写一遍 bigram 概率计算,再跑一次神经网络前向,最后算一次 PPL。这三步走完,后面讨论 Transformer 和 LLM 时,至少不会在基础概念上翻车。希望帮到你。

本文还有配套的精品资源,点击获取

RELATED READING

延伸阅读

更多一线实战笔记与深度复盘,助您持续精进