大模型内部组成与层次调用关系详解
大模型(如GPT-4、Llama 3、Qwen等)并非一个"黑箱",而是一个由多个功能模块和层次结构构成的复杂系统。理解其内部组成与各层之间的调用关系,是掌握大模型工作原理、优化应用性能、进行模型定制与调试的关键。
我们将从两个维度展开:
- 内部组成:大模型的"解剖学"------它由哪些核心组件构成?
- 层次调用关系:大模型的"运行流程"------这些组件如何协同工作?
一、大模型的内部组成:四大核心组件
尽管不同架构(如GPT、PaLM、Mixtral)存在差异,但现代大语言模型(LLM)普遍由以下四个核心组件构成:
┌─────────────────────────────────────────────────────┐
│ 大模型(LLM) │
├──────────────────────┬──────────────────────────────┤
│ 1. 输入嵌入层 (Input Embedding) │
│ 2. Transformer 层堆栈 (Transformer Blocks) │
│ └─ 自注意力机制 (Self-Attention) │
│ └─ 前馈神经网络 (Feed-Forward Network, FFN) │
│ 3. 输出层 (Output Layer) │
│ └─ 解码器头 (Decoder Head) │
│ 4. 上下文管理与缓存 (Context Management & KV Cache) │
└─────────────────────────────────────────────────────┘
1. 输入嵌入层(Input Embedding Layer)
- 功能 :将输入的文本(串行的Token序列 )转换为并行的高维向量(Embedding),作为模型的"数学表示"。
- 技术细节 :
- 分词(Tokenization) :使用BPE(Byte Pair Encoding)或SentencePiece算法将文本切分为Token。
- 例如:"Hello, world!" → ["Hello", ",", "world", "!"]
- 嵌入查找(Embedding Lookup) :每个Token对应一个预训练的向量(如768维、4096维)。
- 位置编码(Positional Encoding) :加入位置信息,让模型知道Token的顺序。
- 方法:绝对位置编码(如BERT)、旋转位置编码(RoPE,用于Llama 3、Qwen)。
- 分词(Tokenization) :使用BPE(Byte Pair Encoding)或SentencePiece算法将文本切分为Token。
- 输出 :一个形状为
[batch_size, seq_len, hidden_size]
的张量。
✅ 关键作用 :将离散的符号(文字)转化为连续的数学空间,供神经网络处理。
2. Transformer 层堆栈(Transformer Blocks Stack)
这是大模型的核心计算引擎 ,通常由数十层(如Llama 3-70B有80层)相同的Transformer块堆叠而成。
每个Transformer块包含两个核心子模块:
(1) 自注意力机制(Self-Attention Mechanism)
- 功能 :让模型在处理每个Token时,能够"关注"序列中的其他相关Token,建立长距离依赖。
- 计算流程 :
- 生成Q、K、V矩阵 :
- Query (Q):当前Token的"查询"向量。
- Key (K):所有Token的"键"向量。
- Value (V):所有Token的"值"向量。
- 计算注意力分数 :
Attention(Q, K, V) = softmax(QK^T / √d_k) * V
- 其中
d_k
是Key向量的维度。
- 多头注意力(Multi-Head Attention) :
- 将Q、K、V拆分为多个"头"(如32头),并行计算注意力,最后拼接。
- 目的:让模型从不同子空间学习不同的语义关系。
- 生成Q、K、V矩阵 :
- 输出:加权后的Value向量,表示每个Token的上下文感知表示。
(2) 前馈神经网络(Feed-Forward Network, FFN)
- 功能 :对自注意力输出的向量进行非线性变换,增强模型的表达能力。
- 结构 :
- 两层全连接网络 + 激活函数(如SwiGLU、ReLU)。
- 公式:
FFN(x) = W2 * σ(W1 * x + b1) + b2
- 特点 :
- 在Transformer块中位于自注意力之后。
- 参数独立于位置,对每个Token单独处理。
✅ 关键作用:Transformer块通过"自注意力 + FFN"的交替堆叠,逐层提取和抽象语义信息。
3. 输出层(Output Layer)
- 功能 :将最后一层Transformer的隐藏状态转换为最终的文本输出。
- 组成 :
- 归一化层(Layer Normalization) :
- 对最后一层的输出进行归一化,稳定训练过程。
- 语言模型头(Language Model Head) :
- 一个线性层(Linear Layer),将隐藏状态映射回词汇表大小(vocab_size)。
- 输出形状:
[batch_size, seq_len, vocab_size]
- Softmax 归一化 :
- 将 logits 转换为概率分布。
- 采样策略(Sampling Strategy) :
- 从概率分布中选择下一个Token。
- 方法:贪心采样(Greedy)、Top-k采样、Top-p(Nucleus)采样、Temperature调整。
- 归一化层(Layer Normalization) :
✅ 关键作用 :将模型的**"思考结果"转化为人类可读的文本。**
4. 上下文管理与缓存(Context Management & KV Cache)
- 功能:管理对话历史,避免重复计算,提升推理效率。
- 关键技术 :
- KV Cache(Key-Value Cache) :
- 在自回归生成过程中,缓存每一层的K和V矩阵。
- 下一个Token生成时,只需计算新Token的Q,并与缓存的K、V计算注意力,无需重新计算整个序列。
- 效果:将推理复杂度从 O(n²) 降低到 O(n),支持长上下文(如128K tokens)。
- 滑动窗口(Sliding Window) :
- 当上下文超过最大长度时,自动丢弃最老的部分。
- 注意力重计算(Recomputation):
- 在训练时节省显存,推理时不常用。
- KV Cache(Key-Value Cache) :
✅ 关键作用:实现高效、低延迟的流式输出和长对话支持。
二、大模型的层次调用关系:一次推理的完整流程
我们以用户输入 "你好,你是谁?"
并生成回复为例,展示大模型内部各组件的调用时序与数据流动。
阶段1:输入处理
用户输入: "你好,你是谁?"
↓
[分词器 Tokenizer]
↓
Token IDs: [151644, 109630, 28757, 109630, 28804, 109630, 28862, 109630, 28804, 13]
↓
[输入嵌入层 Input Embedding]
↓
嵌入向量: [batch=1, seq_len=10, hidden_size=4096] ← Llama 3-8B的hidden_size
阶段2:Transformer 层堆栈前向传播
该嵌入向量依次通过 N 层 Transformer 块(如Llama 3-8B有32层):
For each layer in range(N):
┌──────────────────────────────┐
│ Layer i │
│ │
│ ┌──────────────────────┐ │
│ │ 自注意力 (Self-Attn) │ ←─┼─ 使用上一层输出作为Q,K,V
│ └──────────────────────┘ │
│ ↓ │
│ ┌──────────────────────┐ │
│ │ 前馈网络 (FFN) │ │
│ └──────────────────────┘ │
└──────────────────────────────┘
- 每一层都会更新Token的表示,使其包含更丰富的语义和上下文信息。
- KV Cache 更新:每层计算出的K、V矩阵被缓存,供后续Token生成使用。
阶段3:输出生成(自回归循环)
模型开始逐个生成输出Token:
Step 1: 输入完整Prompt ("你好,你是谁?")
↓
经过所有Transformer层
↓
[输出层] → 得到最后一个Token的logits
↓
Softmax + 采样 → 生成第一个输出Token,如"我"
↓
将"我"追加到输入序列
Step 2: 新输入: "你好,你是谁?我"
↓
只需计算新Token"我"的Q
↓
与缓存的K、V计算注意力(KV Cache)
↓
经过所有Transformer层(仅新Token)
↓
[输出层] → 生成下一个Token,如"是"
↓
重复此过程,直到遇到<EOS>(结束符)
🔁 这是一个**自回归(Autoregressive)**过程,每次只生成一个Token。
阶段4:输出返回
当生成 <EOS>
或达到最大长度时,停止生成。
最终输出: "我是通义千问,阿里巴巴集团旗下的超大规模语言模型。"
↓
[Tokenizer] 解码为文本
↓
返回给用户
三、可视化:大模型内部调用关系图
┌─────────────────────────────────────────────────────────────────────────────┐
│ 大模型推理流程 │
├─────────────────────────────────────────────────────────────────────────────┤
│ 用户输入: "你好,你是谁?" │
│ │
│ ┌─────────────┐ ┌─────────────────┐ ┌──────────────────────────┐ │
│ │ Tokenizer │ ──→ │ Input Embedding │ ──→ │ │ │
│ └─────────────┘ └─────────────────┘ │ │ │
│ │ │ │
│ │ Transformer Block 1 │ │
│ │ ┌─────────┐ ┌──────┐ │ │
│ │ │ Self-Attn│→│ FFN │ │ │
│ │ └─────────┘ └──────┘ │ │
│ │ │ │
│ │ ... │ │
│ │ │ │
│ │ Transformer Block N │ │
│ │ ┌─────────┐ ┌──────┐ │ │
│ │ │ Self-Attn│→│ FFN │ │ │
│ │ └─────────┘ └──────┘ │ │
│ │ │ │
│ └──────────────────────────┘ │
│ ↓ │
│ ┌──────────────────────────┐ │
│ │ Output Layer │ │
│ │ LayerNorm → LM Head │ │
│ │ Softmax → Sampling │ │
│ └──────────────────────────┘ │
│ ↓ │
│ 生成第一个Token: "我" │
│ ↓ │
│ 将"我"追加到输入,循环生成... │
│ │
│ 最终输出: "我是通义千问..." │
└─────────────────────────────────────────────────────────────────────────────┘
总结
大模型的内部是一个精密协作的系统:
- 输入嵌入层:将文字转化为数学向量。
- Transformer 堆栈:通过自注意力和前馈网络逐层提取语义。
- 输出层:将向量转化为文本。
- KV Cache:实现高效自回归生成。
调用关系本质 是一个循环的自回归过程 :
输入 → 嵌入 → 多层Transformer → 输出 → 采样 → 追加输入 → 循环。
理解这一内部结构与调用流程,不仅能帮助我们更好地使用大模型,也为后续的提示工程优化、RAG设计、微调策略制定提供了坚实的理论基础。