从零到精通:手把手教你构建自己的大语言模型(LLM) 本文深入浅出地介绍了大语言模型LLM的原理、构建方法和实际应用。文章首先解释了LLM的基本概念和核心训练任务即通过海量文本数据学习生成通顺的文本内容。接着详细阐述了构建LLM的步骤包括预训练和微调并介绍了Transformer架构和注意力机制等关键技术。文章还提供了具体的代码实现和实验结果展示了如何使用Python和PyTorch在普通电脑上构建和训练LLM。最后总结了从零构建LLM的完整流程强调了理解LLM工作原理的重要性。这篇文章将让你对神秘莫测的大语言模型LLM从这玩意儿到底怎么工作的到哦原来我也能造一个的奇妙转变。咱们一起轻松愉快的发车吧第1章大语言模型是什么鬼1.1 LLM 到底是啥LLMLarge Language Model翻译成人话就是一个特别大的神经网络吃了海量的文本数据然后学会了说人话。但你千万别被骗了——所谓的理解其实是模型能生成看起来通顺、上下文相关的内容它并没有人类的意识。就像鹦鹉会说你好但它并不真的想跟你打招呼。LLM 的核心训练任务特别简单预测下一个词。给你一句话的前半段猜后半段。比如输入“我今天中午吃了——”输出“饭”就这么朴素的逻辑居然能训练出 ChatGPT 这种怪物。这就像你教孩子就教了112结果他自己学会了微积分——研究者自己都觉得很惊讶。1.2 LLM 能干啥翻译、写小说、写代码、做客服、总结文档、回答法律问题……基本上跟文字沾边的事它都能干。现在的 LLM 不仅仅是聊天机器人它正在重新定义我们和技术的交互方式。1.3 构建 LLM 的两步走预训练Pretraining用海量无标注文本训练模型做填空得到一个基础模型foundation model。这一步极其烧钱——GPT-3 的预训练花掉了460 万美元的云计算费用。微调Fine-tuning用少量标注数据进一步训练让它变成某个领域的专家。又分两种自定义的小模型能在特定领域干翻通用大模型而且还省钱、保护隐私、能部署在手机上。苹果公司就在搞这个。1.4 Transformer 架构LLM 的祖宗2017 年的神论文《Attention Is All You Need》提出了 Transformer 架构它有两个子模块编码器Encoder读入输入文本编码成向量解码器Decoder拿编码器的输出生成目标文本原始 Transformer 是用于翻译的编码器读英文解码器吐中文。后来的 BERT 用了编码器部分擅长分类GPT 用了解码器部分擅长生成。本书只做 GPT也就是只用解码器。1.5 海量数据集GPT-3 的训练数据包括CommonCrawl网络爬虫4100 亿 token占 60%WebText2190 亿 tokenBooks1 Books2670 亿 tokenWikipedia30 亿 token总共训练了 3000 亿 token。什么概念如果一个人每秒读一个字不吃不睡要读9.5 万年。1.6 GPT 架构的精髓GPT 本质上就是 Transformer 的解码器部分它通过自回归的方式生成文本——每次预测一个词然后把这个词拼回输入再预测下一个词。GPT-3 有96 层 Transformer、1750 亿参数。这些模型还展现出涌现能力emergent behavior——没专门学过翻译但能翻译没专门学过写诗但能写。就像你本来想养条看门狗结果它自己学会了弹钢琴。1.7 三阶段构建计划本书把构建 LLM 分为三个阶段阶段内容章节Stage 1数据准备 注意力机制第2-3章Stage 2构建 LLM 预训练第4-5章Stage 3微调分类 指令第6-7章(图片来自gptimage_prompt: A three-stage pipeline diagram showing Stage 1 (Data Preparation Attention Mechanism), Stage 2 (GPT Architecture Pretraining), and Stage 3 (Fine-tuning for Classification Instruction Following), with arrows connecting each stage, colorful modern flat design style)第2章跟文本数据打交道——把人话变成机器能啃的饲料2.1 词嵌入给每个词发张身份证神经网络不认识文字只认识数字。所以我们需要嵌入embedding——把每个词映射成一串浮点数。比如猫可能被映射成 [0.43, 0.15, 0.89]狗映射成 [0.41, 0.18, 0.85]。相似的词向量距离近不相似的离得远。GPT-2 Small 的嵌入维度是768GPT-3 最大版是12,288。维度越高能捕捉的关系越细腻但计算量也越大。这就好比用 4K 电视看《猫和老鼠》——画质再好内容还是那只猫追那只老鼠。2.2 分词把句子大卸八块分词tokenization就是把一段话切成小碎片。作者用了一篇叫《The Verdict》的短篇小说20,479 个字符做示例。先用 Python 正则表达式手动实现分词器处理了单词、空格、逗号、句号、问号、引号、双破折号等特殊情况。最终把这篇小说切成了4,690 个 token。2.3 Token → Token ID编号发牌每个唯一 token 分配一个唯一整数 ID。作者实现了 SimpleTokenizerV1 类有 encode文本→ID列表和 decodeID列表→文本两个方法。但有个大问题遇到没见过的词比如Hello直接报 KeyError。2.4 特殊 Token给 LLM 加点暗号为了解决这个问题引入两个特殊 token|unk|表示我不认识这个词|endoftext|分隔不相关的文本片段GPT 系列只用 |endoftext| 就够了其他模型还会用 [BOS]开始、[EOS]结束、[PAD]填充。2.5 Byte Pair EncodingBPEGPT 的秘密武器SimpleTokenizer 遇到未知词就变成 |unk|太粗暴了。GPT 用的是BPE 分词器来自 OpenAI 的 tiktoken 库。BPE 的牛X之处不认识整个词没关系拆成子词甚至单个字符。所以 BPE永远不会遇到 unknown token——它总能把输入拆成它能处理的碎片。GPT-2 的 BPE 词汇表有50,257 个 token。2.6 滑动窗口采样制造训练数据LLM 的训练是预测下一个词所以需要构造输入-输出对。用滑动窗口在文本上移动max_length 控制输入长度stride 控制步长。比如 stride1输入是 [1,2,3]输出就是 [2,3,4]——每次往后挪一位。从一篇短篇小说就能造出海量的训练样本。2.7-2.8 Token 嵌入 位置编码Token ID 经过 nn.Embedding 层变成向量一个大查询表。但嵌入层有个致命缺陷不管词在句子的哪个位置向量都一样。解决方案是位置编码。GPT 用可训练的位置嵌入——每个位置有自己的向量直接加到 token 嵌入上。位置 1 加位置 1 的向量位置 2 加位置 2 的。简单粗暴但有效。(图片来自gptimage_prompt: A flowchart showing text processing pipeline: raw text → tokenization → token IDs → embedding layer → embedding vectors positional encoding → final input vectors, modern flat design with bright colors)第3章注意力机制——让 LLM 学会察言观色3.1 RNN 的记忆缺陷在 Transformer 出来之前RNN 是处理序列数据的主流。它的工作方式是把输入压缩成一个记忆状态然后基于这个状态做生成。但 RNN记不住太长的东西。就像让你传话传了十个人之后原话早就走样了。3.2 注意力的诞生2017 年的 Transformer 论文提出自注意力Self-Attention机制——模型在生成每个词时可以回头看输入序列中的所有位置决定哪些地方更重要。3.3 丐版自注意力先看不带可训练权重的简化版本对于句子中每个词计算它跟所有词的相关性用点积衡量然后 softmax 归一化成概率再用这些概率加权求和所有词的向量——得到上下文向量。这个上下文向量融合了整个句子的信息解决了 RNN 的健忘问题。3.4 完全体缩放点积注意力真正的 LLM 用的是带三个可训练权重矩阵的自注意力WqQuery你在问这段话里谁跟我有关系WkKey每个词在说我的特征是这些WvValue“如果觉得我重要就拿走这个信息”计算步骤输入分别乘 Wq、Wk、Wv 得到 Q、K、Vattn_scores Q K.T算相关性除以 √d_k缩放防止高维度下点积过大导致梯度消失softmax 归一化output attention_weights V得到上下文向量3.5 因果注意力不许开天眼训练时模型不能看到未来的词。比如预测 “I love you” 中的 “you” 时只能看到 “I love”不能偷看答案。实现方式在注意力权重矩阵的右上角加一个上三角掩码把未来位置的权重全变成 0。方法是在 softmax 之前把右上角全设为 -inf这样 softmax 后自然就是 0。还引入了Dropout随机丢弃一部分注意力权重训练时用 0.1-0.2防止过拟合。3.6 多头注意力一个脑袋不够用多头注意力就是并行运行多个因果注意力机制。不同头关注不同信息——一个可能关注语法关系另一个关注语义相似性。GPT-2 Small1.24 亿参数有12 个头嵌入维度 768每个头处理 64 维。高效实现方式先做一次大 QKV 投影然后拆分成多个头用批量矩阵乘法并行计算所有头。第4章搭积木——实现 GPT 模型架构4.1 GPT-2 的身份证GPT-2 Small1.24 亿参数的配置参数值词汇量50,257上下文长度1,024嵌入维度768注意力头数12Transformer 层数12Dropout0.1为什么用 GPT-2 不是 GPT-3因为 GPT-3 的 1750 亿参数在单张 V100 上要训355 年。等你训完世界末日可能都过去好几轮了。4.2 Layer Normalization情绪稳定剂深度神经网络的梯度容易消失或爆炸。层归一化把每一层的输出拉成均值为 0、方差为 1 的标准分布。LayerNorm 不依赖 batch size不像 BatchNorm所以特别适合 LLM 训练。而且它还有可训练的 scale 和 shift 参数——如果模型觉得标准化后不好用它能自己调回去。就像你妈让你把房间收拾整齐但你之后可以把枕头摆歪一点——舒服就行。4.3 GELU比 ReLU 更温柔ReLU 简单粗暴正数留着负数变零。GELU 就温柔多了负数区域也保留非零梯度只是很小。ReLU 像不及格就滚GELU 像不及格还可以补考。前馈网络FeedForward结构Linear(768 → 3072) → GELU → Linear(3072 → 768)。先扩大 4 倍再缩小维度没变但内涵丰富了。4.4 Shortcut Connections高速通道随着网络加深梯度在反向传播时会越来越小。**Shortcut残差连接**就是把输入直接加到输出上给梯度修了一条高速公路。没有 shortcut 时第一层比第五层梯度小 25 倍加了 shortcut各层梯度大小基本一致。4.5 Transformer Block组装成型每个 Transformer Block 的结构LayerNorm → Multi-Head Attention → Dropout → ShortcutLayerNorm → FeedForward → Dropout → Shortcut注意这里用的是Pre-LayerNorm先归一化再进子层比 Post-LayerNorm 训练更稳定。关键是输入输出形状完全一样所以你可以像叠罗汉一样叠 12 层。4.6 GPTModel终极合体GPTModel Token Embedding Positional Embedding 12× TransformerBlock Final LayerNorm Output Head映射到 50,257 维词汇表1.63 亿参数float32 存储需要 621 MB。跟今天 Llama 3 70B存权重就要 140GB比简直是小巫见大巫。4.7 文本生成用 generate_text_simple 做自回归生成输入 “Hello, I am”输出 “Featureiman Byeswickattribute argue”。这是啥玩意儿别急——模型还没训练权重是随机的跟刚出生的婴儿一样话都不会说。第5章预训练——从胡言乱语到能说会道5.1 评估文本质量怎么量化说得好不好交叉熵损失Cross-Entropy Loss模型预测的概率分布跟实际情况差多远。值越小越好。困惑度Perplexity exp(loss)。初始值 48,725相当于模型在 50,257 个词里完全随机乱猜。理想目标接近 1。训练数据集《The Verdict》只有 5,145 个 token90% 训练 / 10% 验证。5.2 训练过程见证 AI 的成长用 AdamW 优化器训练 10 个 epoch约 5 分钟EpochLoss生成文本19.78Every effort moves you, 变逗号复读机26.66Every effort moves you, and, and, and, … and复读机90.54开始输出语法正确的句子100.39能写出通顺的英文句子从逗号复读机到能写出完整句子——这 5 分钟的学习曲线比某些大学生四年的进步还明显。但验证 loss 在第 2 个 epoch 后就停滞在 6.45 了而训练 loss 降到了 0.39——过拟合了。解决办法用更大的数据集。5.3 解码策略让模型有创意而不是背答案贪心解码Greedy Decoding每次选概率最高的 token。安全但无聊像每次都点同一道菜。Temperature 缩放控制随机性。temperature 0.1几乎确定像严谨的科学家temperature 1正常发挥temperature 5放飞自我有 4% 概率生成 “Every effort moves you pizza”Top-k 采样只保留概率最高的 k 个 token 再采样。k3 时“forward、toward、closer” 竞争“pizza” 直接出局。把两者结合先用 top-k 筛选候选池再用 temperature 调整概率分布后再采样。5.4 保存和加载模型保存torch.save(model.state_dict(), model.pth)加载model.load_state_dict(torch.load(model.pth))如果要继续训练记得连 optimizer 状态一起保存——AdamW 记住了每个参数的历史学习率丢了就失忆了。5.5 白嫖 OpenAI 的预训练权重自己训太贵直接用 OpenAI 的 GPT-2 权重下载 498MB 的权重文件需要做一个翻译工作——OpenAI 的变量命名和我们不一样得手动映射。加载成功的标志输入 “Every effort moves you”不再输出乱码而是输出 “toward finding an ideal new way to practice something!”——这才是正常人该说的话。(图片来自gptimage_prompt: Illustration showing pretraining process: unlabeled text data flowing into a GPT model, the model predicting next tokens, loss curve decreasing from high to low over epochs, and the output changing from gibberish to coherent sentences, colorful educational style)第6章分类微调——让 LLM 当专才6.1 微调的两种路子分类微调让模型变成偏科生只会做一件事比如判断垃圾邮件指令微调培养全才能听懂各种指令全才比偏科生难训练得多。作者说得很直白全才难做偏科容易。6.2 准备垃圾邮件数据集用SMS Spam Collection数据集5,572 条短信。原始数据不平衡垃圾 747 vs 正常 4,825用欠采样平衡到 747 vs 747。数据集按 70% 训练、10% 验证、20% 测试拆分。6.3 创建数据加载器短信长短不一用 |endoftext| token 填充到一样长。每个 batch 内所有序列统一长度。6.4 加载预训练权重加载 GPT-2 预训练权重。试一下未经微调的模型你问它这是垃圾邮件吗它不回答只会继续补全文本——光预训练不微调模型就是个复读机。6.5 加装分类头把原来的输出层映射到 50,257 个 token换成新的映射到 2 个类别spam / not spam。技巧冻结大部分参数设置 requires_grad False只训练输出层 最后一个 Transformer block 最后的 LayerNorm只用最后一个 token 的输出做分类——因为因果注意力掩码让最后一个 token 能看到前面所有信息6.6 训练结果超参数AdamW学习率 5e-5weight_decay 0.15 个 epoch。在 M3 MacBook Air 上跑约5.65 分钟指标数值训练集准确率97.21%验证集准确率97.32%测试集准确率95.67%测试集 95.67%相当能打。而且训练和验证曲线贴得很近——没有过拟合nice。6.7 保存模型torch.save(model.state_dict(), classifier.pth)第7章指令微调——让 LLM 当通才7.1 目标把 GPT-2 medium3.55 亿参数训练成一个能听懂人话指令的模型。“把这句话改成被动语态”、“伦敦的首都是哪里”——这些活儿它都得会干。跟分类微调不同指令微调不限制输出——输出空间大得没边难度高得多。7.2 准备指令数据集1,100 条指令-回答对JSON 格式每条包含 instruction、input、output 三个字段。使用Alpaca 格式组织 promptInstruction: 把下句改成被动语态Input: The chef cooks the meal.Response: The meal is cooked by the chef.数据集划分85% 训练935 条、10% 测试110 条、5% 验证55 条。7.3 自定义 Collate 函数指令长度不一需要每个 batch 各自填充到当前 batch 的最长长度而不是整个数据集的最长长度。这样节省大量计算和内存。关键技巧把 padding token 在 target 中对应的位置设为-100。PyTorch 的交叉熵损失默认忽略 -100这样 padding 部分就不会参与损失计算。不然模型会去学预测那些无聊的填充 token。7.4 加载 GPT-2 medium355M为什么用 3.55 亿参数而不是 1.24 亿因为指令微调任务复杂小模型撑不住。没微调的模型试一下让它把主动句改被动句——它直接复读原句还顺带重抄了一遍指令。就像学生考试时把题目抄了一遍当答案。7.5 正式微调超参数AdamW学习率 5e-5只跑 2 个 epoch数据集小再多就过拟合了。在 A100 GPU 上只需52 秒。训练 loss 从 2.637 降到 0.300。第 1 个 epoch 结束已经能把 “The chef cooks the meal every day.” 改成 “The meal is prepared every day by the chef.”——虽然用了 “prepared” 而不是标准答案的 “cooked”但语法和语义完全正确。第 2 个 epoch 结束变成正确的 “The meal is cooked every day by the chef.”7.6 评估人工评估 110 条回复太累用另一个 LLMLlama 3 8B来打分评分 prompt 里包含指令 标准答案 模型回答让 Llama 3 从 0-100 打分。测试样例“快如子弹”标准答案是快如闪电→85 分没毛病但不够精确“积云”标准答案是积雨云→40 分方向对了但答错了“简·奥斯汀” →95 分接近完美但稍微啰嗦了点110 条测试集平均分50.32 分。可以用来做基准对比。假如你从2026年开始学大模型按这个步骤走准能稳步进阶。接下来告诉你一条最快的邪修路线3个月即可成为模型大师薪资直接起飞。阶段1:大模型基础阶段2:RAG应用开发工程阶段3:大模型Agent应用架构阶段4:大模型微调与私有化部署配套文档资源全套AI 大模型 学习资料朋友们如果需要可以微信扫描下方二维码免费领取【保证100%免费】配套文档资源全套AI 大模型 学习资料朋友们如果需要可以微信扫描下方二维码免费领取【保证100%免费】