【AI基础篇05】注意力机制:Self-Attention详解

前言:如果说Transformer是大模型时代的"地基",那注意力机制就是这块地基里的"钢筋"。它让模型能够从长序列中"关注"最重要的信息,而不是像RNN那样一步步传递。但Self-Attention到底在做什么?Q、K、V三个矩阵是干嘛的?为什么需要多头?为什么DeepSeek要用MLA替代标准Attention?本文从零讲透。


📋 目录


一、为什么需要注意力机制?

1.1 注意力机制之前的世界

在Transformer出现之前,序列模型主要靠RNN/LSTM:

RNN处理长句的过程:
"我今天早上在地铁上读了一本关于AI的..." 
  → 读到"AI"时,前面"地铁"的信息已经衰减了80%
  → 读到句尾时,开头信息几乎为0

问题:长距离依赖丢失
  解决方案:LSTM用门控缓解,但不能根治
  本质原因:信息必须串行传递,不能跳跃

1.2 注意力机制的直觉

注意力 = 加权求和

想象你在看一张满是人的合照,要找你的朋友:

  • 关注那些像你朋友的面孔(分配高权重)
  • 忽略那些不像的面孔(分配低权重)
  • 最终结论基于你关注的那些面孔

注意力机制做的也是同样的事:

  • 给重要的位置高权重
  • 给不重要的位置低权重
  • 输出是所有位置的加权和
如果没有注意力(RNN):
  "我" → "爱" → "你" 
  信息沿着链传递,"我"的信息到"你"时已经模糊

有了注意力(Transformer):
  "我" "爱" "你"
  每个词直接关注所有位置:
    "我" → 关注"爱"(75%)、"你"(20%)、"我"(5%)
    "你" → 关注"爱"(70%)、"我"(25%)、"你"(5%)
  任何两个词之间都是直接路径!

二、核心思想:Query、Key、Value

2.1 类比:图书馆检索

理解Q、K、V的最佳方式是类比图书馆检索:

你在图书馆找书的过程:

1. Query(你的需求)📝
   → "我想要一本关于深度学习的书"
   → 这是你的查询需求

2. Key(书目索引)🏷️
   → 每本书的标题、关键词、简介
   → 系统把你的Query和每本书的Key做匹配

3. Value(实际内容)📖
   → 每本书的完整内容
   → 匹配到后,你取出这本书的内容

4. Attention Score(匹配度)⭐
   → "深度学习导论" 匹配度 95%
   → "Python入门"    匹配度 5%
   → "高等数学"      匹配度 0%

5. 最终结果:
   → 95% × "深度学习导论"的内容 + 5% × "Python入门"的内容
   → 权重越高,对最终输出的贡献越大

2.2 在Transformer中的对应

输入句子:"I love AI"

Step 1:每个词向量通过三个矩阵生成Q、K、V
  "I"的词向量 [0.1, 0.5, ...]
    → Q_I = W_Q × [0.1, 0.5, ...]  ← 查询向量
    → K_I = W_K × [0.1, 0.5, ...]  ← 键向量
    → V_I = W_V × [0.1, 0.5, ...]  ← 值向量

  "love"的词向量
    → Q_L, K_L, V_L

  "AI"的词向量
    → Q_A, K_A, V_A

Step 2:每个词用它的Q去匹配所有词的K
  Q_I 匹配 K_I → score_II  
  Q_I 匹配 K_L → score_IL  
  Q_I 匹配 K_A → score_IA  

  Q_L 匹配 K_I → score_LI
  Q_L 匹配 K_L → score_LL
  Q_L 匹配 K_A → score_LA
  ...

Step 3:Softmax转为权重 + 加权求和
  "I"的输出 = softmax([score_II, score_IL, score_IA]) × [V_I, V_L, V_A]

2.3 一句话总结

Query是你"想找什么",Key是每个位置的"标签",Value是每个位置的"内容"。注意力机制就是用Query去匹配Key,得到权重,再用权重去加权Value。


三、数学公式拆解:Attention一步步来

3.1 标准公式

Attention(Q, K, V) = softmax(Q × K^T / √d_k) × V

其中:
  Q: Query矩阵,形状 [序列长度, d_k]
  K: Key矩阵,形状 [序列长度, d_k]  
  V: Value矩阵,形状 [序列长度, d_v]
  d_k: Query/Key的维度
  √d_k: 缩放因子

3.2 逐步拆解

假设输入序列长度=3,d_k=4:

Step 1: Q × K^T(计算所有pair的相似度)

Q = [q1]    K^T = [k1^T k2^T k3^T]  
    [q2]         
    [q3]         

结果矩阵 S = Q × K^T(3×3):
  S[1][1] = q1·k1  → "I"看"自己"的相似度
  S[1][2] = q1·k2  → "I"看"love"的相似度
  S[1][3] = q1·k3  → "I"看"AI"的相似度
  S[2][1] = q2·k1  → "love"看"I"的相似度
  ...

直观理解:
  点积越大 → 两个向量越相似 → 注意力权重越高
  q1·k2 很大 → "I"和"love"很相关(语法上主语+动词)
  q1·k3 较小 → "I"和"AI"不太相关
Step 2: 缩放 S / √d_k

为什么除以√d_k?
  当d_k很大时,点积的结果会很大(因为很多维度加起来)
  大的点积进入softmax后会让梯度变得非常小(梯度消失)
  除以√d_k把方差控制到1,保持梯度稳定

举例:
  设d_k=512,q和k是均值为0、方差为1的随机向量
  点积的方差 ≈ d_k = 512
  除以√d_k = √512 ≈ 22.6 后,方差回到1
Step 3: Softmax(归一化为概率分布)

原始分数:           [2.0, 5.0, 1.0, 3.0]
                    ↓ softmax
注意力权重:         [0.07, 0.63, 0.02, 0.28]

作用:
  1. 归一化到[0,1]区间
  2. 让高分更高,低分更低(竞争机制)
  3. 所有权重之和=1
Step 4: Weighted Sum(加权求和)

假设V矩阵:
  V1 = [0.1, 0.2, 0.3]
  V2 = [0.4, 0.5, 0.6]
  V3 = [0.7, 0.8, 0.9]

权重分布:[0.2, 0.5, 0.3]

输出 = 0.2×V1 + 0.5×V2 + 0.3×V3
     = [0.02+0.20+0.21, 0.04+0.25+0.24, 0.06+0.30+0.27]
     = [0.43, 0.53, 0.63]

3.3 完整计算流程图

输入: "I love AI"
        ↓
Embedding → [x1, x2, x3]  
        ↓
三个线性投影:
  Q = X × W_Q   ← 学习"我想关注什么"
  K = X × W_K   ← 学习"我有什么可以被人关注"
  V = X × W_V   ← 学习"我实际贡献什么内容"
        ↓
注意力分数矩阵 S = Q × K^T / √d_k
        ↓
注意力权重 W = softmax(S, dim=-1)
        ↓
输出 O = W × V
        ↓
最终:每个位置都"看到"了所有位置的信息

💡 面试加分点:Q、K、V三个矩阵的维度可以不同,但Q和K的最后一维必须相同(因为要做点积),V的最后一维决定输出维度。在实际实现中,通常d_k = d_v。


四、Self-Attention vs Cross-Attention

4.1 Self-Attention(自注意力)

定义:Q、K、V都来自同一个输入序列

"我爱AI"
  → Q来自"I love AI"
  → K来自"I love AI"  
  → V来自"I love AI"

作用:
  ✅ 捕捉序列内部的关系
  ✅ 每个词理解它和序列中其他词的关系
  ✅ 解决长距离依赖问题

应用:
  - Transformer的Encoder层
  - BERT的每一层
  - GPT的每一层(带掩码)

4.2 Cross-Attention(交叉注意力)

定义:Q来自一个序列,K和V来自另一个序列

翻译任务(Encoder-Decoder):
  Encoder输出:"I love AI" → 生成K_enc, V_enc
  Decoder输入:"我爱" → 生成Q_dec
  
  Q_dec × K_enc^T → 当前输出"我爱"时,参考"AI"的权重最大

作用:
  ✅ 两个序列之间的信息交互
  ✅ 一个序列"看"另一个序列

应用:
  - Transformer的Decoder层
  - T5的Cross-Attention
  - 多模态:文本Q × 图像K,V

4.3 直观对比

Self-Attention(自我对话):
  "我今天很开心" → 每个词看其他词
  开 → 看"很" → 程度副词
  开 → 看"心" → 快乐相关
  输出:带了上下文的"开"

Cross-Attention(对话交流):
  源语言:"I love AI"
  目标语言:当前已生成"我",要生成"爱"
  "爱"的Q → 看"I love AI" → "love"权重最大 → 输出"love"对应词

五、Multi-Head Attention:多头并行

5.1 为什么需要多头?

单头注意力的局限:
  一个"注意力模式"不够用

  在"我今天去银行办理业务"中:
    注意力模式1(语法关系):"办理" → "业务"(动宾)
    注意力模式2(语义关系):"银行" → "业务"(相关)
    注意力模式3(代词指代):没有代词,不需要

  单头只能学一种模式!→ 多头并行学习多种模式

5.2 多头的工作原理

输入:"我今天很开心"
        ↓
线性投影 → 拆成8个头(每个头独立做Attention)

头1:关注语法关系
   "很" → "开"(程度副词+形容词)
   "我" → "今天"(主语+时间状语)

头2:关注语义相似
   "开" → "心"("开心"是一个词)
   "天" → "很"(不相关,权重低)

头3:关注位置关系
   相邻词之间权重高
   ...

头8:关注远距离依赖
   "我" ← → "开心"(主语和表语的关系)
        ↓
8个头的结果拼接 + 线性投影 → 最终输出

5.3 数学形式

MultiHead(Q, K, V) = Concat(head_1, ..., head_h) × W_O

其中 head_i = Attention(Q×W_Q_i, K×W_K_i, V×W_V_i)

参数说明:
  h: 头数(GPT-4使用96头)
  d_k: 每个头的维度(通常 = d_model / h)
  W_O: 输出投影矩阵

5.4 各模型的头配置

模型 d_model 头数 每头维度 特点
BERT-base 768 12 64 经典配置
GPT-3 12288 96 128 超大参数
LLaMA-2 70B 8192 64 128 分组查询(GQA)
DeepSeek-V3 7168 128 56 使用MLA替代MHA
Claude 3.5 非公开 具体参数未公开

六、Causal Attention:因果掩码

6.1 为什么需要掩码?

在语言模型生成文本时,一个关键约束:
  "我今天去___"
  要预测"去"后面的词时,不能看到答案!
  
  如果模型能看到后面:
    "我今天去上学" → 预测"去"时已经看到了"上学"
    → 这等于作弊!模型不需要真正理解语言
  
  所以:每个位置只能看到自己和前面的词

6.2 Causal Mask的实现

注意力分数矩阵(3×3):
           I    love   AI
     I    [s_II, s_IL, s_IA]
   love  [s_LI, s_LL, s_LA]
    AI   [s_AI, s_AL, s_AA]

加上因果掩码(上三角矩阵设为-∞):
           I    love   AI
     I    [s_II,  -∞,   -∞]
   love  [s_LI, s_LL,  -∞]
    AI   [s_AI, s_AL, s_AA]

Softmax后:
           I    love   AI
     I    [1.0,  0.0,  0.0]
   love  [0.3,  0.7,  0.0]
    AI   [0.1,  0.3,  0.6]

意义:
  位置1(I):只能看到自己
  位置2(love):能看到I和love
  位置3(AI):能看到I、love和AI

6.3 三种不同的Mask

✅ Causal Mask(GPT类模型 - 自回归生成)
  [1, 0, 0]
  [1, 1, 0]
  [1, 1, 1]
  每个token只能看到自己和自己之前的token

✅ Padding Mask(BERT类模型 - 批处理)
  [1, 1, 1, 1, 0, 0]  ← 后两个是pad
  忽略无效的填充位置

✅ Cross-Attention Mask(Encoder-Decoder模型)
  Decoder每个位置可以看到Encoder所有位置
  但Decoder内部是causal的

💡 面试加分点:GPT和BERT的核心架构差异就在Mask——GPT用Causal Mask(只能看左边),BERT用双向Mask(能看两边)。这也是为什么GPT擅长生成,BERT擅长理解。


七、注意力机制的演进:MHA→MQA→GQA→MLA

这是2024-2026年注意力机制最重要的演进路线。核心问题:推理时KV Cache太大怎么办?

7.1 问题背景

推理时,大语言模型要缓存每个token的K和V(KV Cache):

MHA(标准多头注意力):
  每个头缓存自己的K和V
  模型: 32层 × 32头 × 128维 × 2(K,V) = 每token 262,144个值
  1024个token → 约268M个值(单次推理)

问题:
  KV Cache随序列长度线性增长
  长上下文时(1M tokens),KV Cache会吃掉大量显存
  这也是为什么长上下文推理成本高

7.2 演进路线对比

MHA (Multi-Head Attention) —— 2017, Transformer原始
  ├── 每个头独立K、V
  ├── KV缓存: O(n × h × d_h)  ← 最大
  └── 表达能力: 最强

MQA (Multi-Query Attention) —— 2019, 减少缓存
  ├── 所有头共享一组K、V
  ├── KV缓存: O(n × d_h)  ← 缩小h倍
  └── 表达能力: 较弱(单一K、V无法区分不同头)

GQA (Grouped Query Attention) —— 2023, LLaMA 2
  ├── 多个查询头共享一组K、V(折中方案)
  ├── KV缓存: O(n × g × d_h) ← g为组数
  └── 表达能力: 中等(组内共享)

7.3 MLA:DeepSeek的突破(2024-2026)

MLA (Multi-Head Latent Attention) —— DeepSeek V2/V3/R1

核心思想:把KV压缩到低维"潜在空间"再缓存

传统方式:缓存完整的K、V矩阵
  K维度: 128头 × 128维 ≈ 16,384
  V维度: 128头 × 128维 ≈ 16,384

MLA方式:缓存压缩后的"潜向量"
  潜向量维度: 2,048(压缩比 8:1)
  
  推理时,从潜向量"解压缩"出K、V

效果:
  KV缓存减少约 87.5%
  DeepSeek-V3中:KV缓存从6.8GB降至3.2GB
  推理延迟从89ms降至42ms

7.4 四代注意力对比

机制 提出时间 代表模型 KV缓存大小 表达能力 综合效率
MHA 2017 Transformer O(n·h·d_h) ★★★★★ ★★★
MQA 2019 PaLM O(n·d_h) ★★★ ★★★★
GQA 2023 LLaMA 2/3 O(n·g·d_h) ★★★★ ★★★★
MLA 2024 DeepSeek-V3/R1/V4 O(n·d_c) ★★★★★ ★★★★★

💡 2026年趋势:MLA正在成为下一代大模型的标配。DeepSeek已在其V4-Pro中进一步优化MLA,配合FlashMLA推理内核,实现了速度与内存的双重突破。TransMLA技术还能将现有的GQA模型无损转换为MLA——这意味着未来的LLaMA 4也可能拥抱MLA。


八、Flash Attention:加速注意力计算

8.1 问题:注意力计算的瓶颈

标准注意力计算的问题:
  S = Q × K^T   → 形状 [n, n]  ← 内存占用O(n²)
  P = softmax(S)  ← 需要读写n×n矩阵
  O = P × V     ← 需要读写n×n矩阵

对于n=4096:
  注意力矩阵大小: 4096×4096 × 4字节 ≈ 67MB(单层)
  32层 → 2.1GB(单次前向传播)

瓶颈不在计算,在内存带宽!
GPU计算极快,但读写内存很慢

8.2 Flash Attention的原理

传统方法:
  1. 把Q、K、V从慢速HBM读到快速SRAM
  2. 计算S = Q×K^T,把S写回HBM
  3. 把S读回SRAM,计算softmax
  4. 再写回HBM...

  → 反复读写HBM!极度浪费带宽

Flash Attention(三块核心优化):

1️⃣ Tiling(分块计算)
  不一次性计算完整的n×n矩阵
  把Q、K、V切成小块,逐块计算
  在SRAM小内存内完成全部计算
  → 减少HBM读写次数

2️⃣ 在线Softmax(recomputation)
  不保存中间注意力矩阵
  反向传播时重新计算
  → 空间换时间

3️⃣ 内核融合(Kernel Fusion)
  把多个小算子合并为一个大算子
  减少kernel launch开销

结果:
  训练速度提升2-3倍
  HBM读写减少5-10倍
  显存占用降低

8.3 Flash Attention的发展

Flash Attention v1 (2022): Tri Dao 提出
  - 基础分块+在线softmax
  - 2x速度提升

Flash Attention v2 (2023):
  - 减少非矩阵乘法操作
  - 优化线程束调度
  - 1.5-2x相对v1提升

Flash Attention v3 (2024):
  - 针对Hopper GPU优化
  - 使用FP8低精度
  - 支持更长的序列

👇

2026年现状:
  所有主流训练框架已默认集成Flash Attention
  训练128K序列不再是问题
  H100上处理128K序列仅需数毫秒

九、注意力机制的局限与挑战

9.1 核心问题

问题1:O(n²)计算复杂度
  序列长度翻倍 → 计算量翻4倍
  1K tokens: 1M次计算
  128K tokens: 16G次计算(1.6万倍)
  
  影响:长上下文训练成本极高

问题2:位置编码依赖
  注意力本身没有位置概念
  "我喜欢猫"和"猫喜欢我"是不同的
  需要额外的位置编码(如RoPE)

问题3:注意力分散
  序列越长,注意力越"均匀"
  有用信息被淹没在大量噪声中
  这也是为什么长上下文models仍有挑战

9.2 替代架构探索

Mamba / State Space Model (SSM)
  用状态空间模型替代注意力
  复杂度:O(n) vs 注意力 O(n²)
  效果:在部分任务上接近Transformer
  主要问题:无法直接做交叉注意力

混合架构(2025-2026趋势)
  Mamba-2 + Attention 混合层
  前几层用SSM(高效处理全局)
  后几层用Attention(精细交互)
  
  代表:Jamba、Zamba
  
  结论:Attention短期内不会被完全替代
  但"纯Attention"的架构正在向混合架构演进

9.3 2026年注意力机制全景

┌─────────────────────────────────────────────┐
│              注意力机制演进                   │
├─────────────────────────────────────────────┤
│ 2017 MHA     ‖ Transformer诞生               │
│ 2019 MQA     ‖ PaLM减少KV缓存                │
│ 2022 FlashAtt‖ 注意力计算加速10倍             │
│ 2023 GQA     ‖ LLaMA 2折中方案               │
│ 2024 MLA     ‖ DeepSeek压缩KV 87.5%          │
│ 2025 TransMLA‖ GQA→MLA无损转换               │
│ 2026 FlashMLA‖ 专用推理内核,变长序列优化      │
│ 2026 混合架构‖ SSM+Attention,取长补短        │
└─────────────────────────────────────────────┘

十、实战:用代码理解Attention

10.1 从零实现Scaled Dot-Product Attention

import torch
import torch.nn.functional as F

def scaled_dot_product_attention(Q, K, V, mask=None):
    """
    从零实现缩放点积注意力
    
    参数:
        Q: Query, shape [batch, heads, seq_len, d_k]
        K: Key,   shape [batch, heads, seq_len, d_k]
        V: Value, shape [batch, heads, seq_len, d_v]
        mask: 可选的注意力掩码
    返回:
        output: 注意力输出
        attention_weights: 注意力权重
    """
    d_k = Q.size(-1)
    
    # Step 1: Q × K^T / √d_k
    scores = torch.matmul(Q, K.transpose(-2, -1)) / torch.sqrt(torch.tensor(d_k, dtype=torch.float32))
    
    # Step 2: 应用掩码(如果有的话)
    if mask is not None:
        scores = scores.masked_fill(mask == 0, float('-inf'))
    
    # Step 3: Softmax
    attention_weights = F.softmax(scores, dim=-1)
    
    # Step 4: 加权求和 × V
    output = torch.matmul(attention_weights, V)
    
    return output, attention_weights

# 测试
batch_size, heads, seq_len, d_k = 1, 2, 4, 8
Q = torch.randn(batch_size, heads, seq_len, d_k)
K = torch.randn(batch_size, heads, seq_len, d_k)
V = torch.randn(batch_size, heads, seq_len, d_k)

output, weights = scaled_dot_product_attention(Q, K, V)
print(f"输出形状: {output.shape}")
print(f"注意力权重形状: {weights.shape}")
print(f"注意力权重(第一个头):\n{weights[0, 0]}")

10.2 多头注意力完整实现

import torch
import torch.nn as nn

class MultiHeadAttention(nn.Module):
    """标准多头注意力实现"""
    
    def __init__(self, d_model, n_heads, dropout=0.1):
        super().__init__()
        assert d_model % n_heads == 0, "d_model必须能被n_heads整除"
        
        self.d_model = d_model
        self.n_heads = n_heads
        self.d_k = d_model // n_heads
        
        # Q、K、V的线性投影
        self.W_Q = nn.Linear(d_model, d_model)
        self.W_K = nn.Linear(d_model, d_model)
        self.W_V = nn.Linear(d_model, d_model)
        
        # 输出投影
        self.W_O = nn.Linear(d_model, d_model)
        
        self.dropout = nn.Dropout(dropout)
        
    def forward(self, Q, K, V, mask=None):
        batch_size = Q.size(0)
        
        # Step 1: 线性投影 + 拆分为多头
        Q = self.W_Q(Q).view(batch_size, -1, self.n_heads, self.d_k).transpose(1, 2)
        K = self.W_K(K).view(batch_size, -1, self.n_heads, self.d_k).transpose(1, 2)
        V = self.W_V(V).view(batch_size, -1, self.n_heads, self.d_k).transpose(1, 2)
        
        # Step 2: Scaled Dot-Product Attention
        scores = torch.matmul(Q, K.transpose(-2, -1)) / torch.sqrt(torch.tensor(self.d_k, dtype=torch.float32))
        
        if mask is not None:
            scores = scores.masked_fill(mask == 0, float('-inf'))
        
        attention_weights = F.softmax(scores, dim=-1)
        attention_weights = self.dropout(attention_weights)
        
        context = torch.matmul(attention_weights, V)
        
        # Step 3: 合并所有头
        context = context.transpose(1, 2).contiguous().view(batch_size, -1, self.d_model)
        
        # Step 4: 输出投影
        output = self.W_O(context)
        
        return output, attention_weights

# 使用示例
mha = MultiHeadAttention(d_model=512, n_heads=8)
x = torch.randn(2, 10, 512)  # batch=2, seq_len=10, d_model=512
output, attn = mha(x, x, x)  # Self-Attention: Q=K=V=x
print(f"多头注意力输出形状: {output.shape}")  # [2, 10, 512]

10.3 Causal Mask + Flash Attention(PyTorch 2.0+)

import torch

def generate_causal_mask(seq_len):
    """生成因果掩码"""
    mask = torch.tril(torch.ones(seq_len, seq_len))
    return mask

# PyTorch 2.0+ 内置的scaled_dot_product_attention
# 自动使用Flash Attention(如果GPU支持)
batch_size, n_heads, seq_len, d_k = 2, 8, 128, 64

Q = torch.randn(batch_size, n_heads, seq_len, d_k)
K = torch.randn(batch_size, n_heads, seq_len, d_k)
V = torch.randn(batch_size, n_heads, seq_len, d_k)

# 生成causal mask
attn_mask = generate_causal_mask(seq_len)

# 使用PyTorch的Flash Attention(自动选择最佳实现)
with torch.backends.cuda.sdp_kernel(enable_flash=True, enable_math=False, enable_mem_efficient=False):
    output = F.scaled_dot_product_attention(
        Q, K, V,
        attn_mask=attn_mask,
        dropout_p=0.1,
        is_causal=True  # 或者直接设置is_causal=True,比手动传mask更高效
    )

print(f"Flash Attention输出形状: {output.shape}")

# 检查是否真的使用了Flash Attention
print(f"是否使用Flash Attention: {torch.backends.cuda.flash_sdp_enabled()}")

# 性能对比(序列长度=4096时差距最明显)
import time

seq_len_large = 4096
Q_large = torch.randn(1, 8, seq_len_large, 64).cuda()
K_large = torch.randn(1, 8, seq_len_large, 64).cuda()
V_large = torch.randn(1, 8, seq_len_large, 64).cuda()

# 手动实现(慢)
start = time.time()
scores = torch.matmul(Q_large, K_large.transpose(-2, -1)) / 8
attn = F.softmax(scores, dim=-1)
out_manual = torch.matmul(attn, V_large)
print(f"手动注意力耗时: {time.time() - start:.3f}s")

# Flash Attention(快)
start = time.time()
out_flash = F.scaled_dot_product_attention(Q_large, K_large, V_large, is_causal=True)
print(f"Flash Attention耗时: {time.time() - start:.3f}s")

📌 总结

注意力机制核心要点:

1️⃣ 本质:加权求和
   输入 → Q/K/V投影 → 相似度计算 → Softmax归一化 → 加权输出
   Query找什么,Key有什么,Value贡献什么

2️⃣ Q/K/V的意义
   Q = "我想关注什么"
   K = "我有什么值得关注"
   V = "我实际贡献的内容"

3️⃣ 多头注意力
   多组Q/K/V并行 → 捕捉不同关系模式
   GPT-4有96个头,每个头学不同的偏重

4️⃣ Causal Mask
   确保自回归生成时"看不到未来"
   GPT和BERT的核心架构差异

5️⃣ 演进路线(2026年最新)
   MHA(2017) → MQA(2019) → GQA(2023) → MLA(2024)
   Flash Attention让训练加速2-3倍
   MLA让KV缓存减少87.5%

6️⃣ 局限
   O(n²)复杂度是硬伤
   Mamba等替代方案仍在探索
   2026趋势:混合架构(SSM+Attention)


🔗 延伸阅读

  • 【AI基础篇01】AI大模型基础概念全景图
  • 【AI基础篇02】从Transformer到GPT:生成式AI的演进史
  • 【AI基础篇03】大模型参数、算力、数据:Scaling Law的本质
  • 【AI基础篇04】Tokenization:文本如何变成数字,为什么分词器这么重要
  • 【AI基础篇06】位置编码:为什么需要它?

觉得有帮助?点赞收藏!下一篇我们讲位置编码——Attention本身没有"位置"概念,那模型怎么知道"我爱你"和"你爱我"的区别? 🚀

标签:人工智能、注意力机制、Self-Attention、Multi-Head Attention、Transformer、MLA、Flash Attention、DeepSeek

Logo

AtomGit 是由开放原子开源基金会联合 CSDN 等生态伙伴共同推出的新一代开源与人工智能协作平台。平台坚持“开放、中立、公益”的理念,把代码托管、模型共享、数据集托管、智能体开发体验和算力服务整合在一起,为开发者提供从开发、训练到部署的一站式体验。

更多推荐