自注意力机制是深度学习、自然语言处理、Transformer、大语言模型和多模态模型中非常核心的一个术语。它用来描述一种让序列中每个位置主动“查看”同一序列中其他位置并根据相关程度汇总信息的计算方法。换句话说自注意力机制是在回答模型怎样判断一句话中哪些词彼此更相关并把重要上下文信息融合到当前表示中。如果说 RNN 按顺序一步步读取文本CNN 主要关注局部窗口内的信息那么自注意力机制更强调“全局关联”。它允许一个 token 在一次计算中直接关注序列中的其他 token而不必只依赖相邻位置逐步传递信息。因此自注意力机制常用于 Transformer、BERT、GPT、大语言模型、机器翻译、文本理解、文本生成、图像 Transformer、多模态大模型和扩散模型中的条件建模是理解现代人工智能模型结构的重要基础概念。一、基本概念什么是自注意力机制自注意力机制Self-Attention是一种在同一个序列内部计算元素之间关系的方法。例如一个句子这只猫坐在垫子上因为它很舒服。这里的“它”到底指什么需要结合前文判断。自注意力机制可以让“它”这个 token 去关注前面的“猫”“垫子”等 token并根据相关程度汇总上下文信息。从通俗角度看自注意力机制像是在句子内部给每个词安排一次“查阅上下文”的机会。每个 token 不只是看自己还会问当前这个 token 应该重点参考哪些其他 token例如在句子中我喜欢机器学习因为它能发现数据中的规律。“它”可能需要重点关注“机器学习”而不是“我”。自注意力机制的目标就是让模型自动学习这种关联关系。在一个长度为 L 的序列中每个 token 都可以和其他 token 建立联系。经过自注意力计算后每个位置都会得到一个融合上下文的新表示。可以简单理解为原始 token 表示 → 计算 token 之间的相关性 → 加权汇总上下文 → 新的 token 表示因此自注意力不是简单地找关键词而是让模型根据训练任务自动学习“哪些位置对当前表示更重要”。二、为什么需要自注意力机制自注意力机制之所以重要是因为语言、图像和多模态数据中都存在复杂的上下文关系。在自然语言中一个词的含义常常依赖其他词。例如苹果发布了新产品。这里的“苹果”更可能指公司。而在我吃了一个苹果。这里的“苹果”更可能指水果。同一个词在不同上下文中含义可能不同。自注意力机制可以让模型根据上下文动态调整每个 token 的表示。它的主要作用包括• 建立序列中不同位置之间的关联• 捕捉长距离依赖关系• 根据上下文调整词语含义• 支持并行计算• 为 Transformer 提供核心计算结构普通 RNN 需要按顺序传递信息。如果两个词相距很远信息要经过很多时间步才能传到。自注意力机制则可以让任意两个 token 直接建立联系。从通俗角度看RNN 像排队传话一个词的信息要一站站传过去。自注意力像开会讨论每个词都可以直接听取其他词的意见。这也是 Transformer 能够在大规模语言模型中广泛使用的重要原因之一。三、Q、K、V自注意力中的三个角色自注意力机制中最常见的三个概念是• Query查询常记作 Q• Key键常记作 K• Value值常记作 V这三个名字看起来抽象但可以用“查资料”来理解。1、Query当前想找什么Query 表示当前位置发出的查询。它代表当前 token 想从上下文中寻找什么信息。例如“它”这个 token 可能会发出一个查询我应该指代谁2、Key每个位置提供的匹配线索Key 表示每个 token 提供给别人匹配的线索。模型会用 Query 和 Key 计算相关性。如果某个 token 的 Key 与当前 Query 很匹配说明它对当前 token 可能重要。3、Value真正被汇总的信息Value 表示每个 token 实际提供的信息内容。注意力权重计算出来后会对 Value 做加权求和得到当前位置的新表示。从通俗角度看• Q我在找什么• K你能不能匹配我的需求• V如果匹配我从你那里取走什么信息例如当前 token 是“它”。它的 Query 会和其他 token 的 Key 做匹配。如果“机器学习”的 Key 与“它”的 Query 很相关那么“机器学习”的 Value 就会以较大权重参与“它”的新表示。在实际模型中Q、K、V 都是由输入向量通过线性变换得到的其中• X 表示输入序列的向量矩阵• W_Q、W_K、W_V 表示可学习的权重矩阵• Q、K、V 分别表示查询矩阵、键矩阵和值矩阵这说明 Q、K、V 不是人工指定的而是在训练过程中学习出来的表示。四、自注意力的核心计算过程自注意力的核心计算可以分成四步生成 Q、K、V → 计算相关性分数 → 归一化为注意力权重 → 加权汇总 Value图 1自注意力机制的基本计算流程1、生成 Q、K、V给定输入序列向量 X先通过三个不同的线性变换得到 Q、K、V其中• X 表示输入 token 表示• W_Q、W_K、W_V 是可学习参数• Q、K、V 是自注意力计算需要的三组向量2、计算相关性分数用 Q 和 K 计算 token 之间的相关性。常见做法是点积其中• S 表示相关性分数矩阵• Q 表示查询矩阵• Kᵀ 表示 K 的转置如果第 i 个 token 的 Query 与第 j 个 token 的 Key 点积较大说明第 i 个 token 更应该关注第 j 个 token。为了避免分数过大通常会除以 √d_k其中• d_k 表示 Key 向量维度• √d_k 用于缩放点积结果使训练更稳定3、归一化为注意力权重接着使用 softmax 把相关性分数变成权重其中• A 表示注意力权重矩阵• softmax 让每一行权重加起来为 1每一行可以理解为当前 token 对所有 token 的关注比例例如它 → 机器学习0.65它 → 我0.10它 → 喜欢0.08它 → 规律0.17这表示“它”更大程度参考“机器学习”。4、加权汇总 Value最后用注意力权重 A 对 V 做加权求和其中• O 表示自注意力输出• A 表示注意力权重• V 表示值矩阵完整公式通常写为从通俗角度看自注意力先判断“该看谁”再把被关注位置的信息按权重汇总起来。五、注意力矩阵谁关注谁自注意力机制会产生一个注意力矩阵。图 2注意力矩阵示意图假设序列长度为 L那么注意力矩阵的形状通常是其中• 行表示当前正在更新的 token• 列表示被它关注的 token• 每个元素表示一个关注权重例如对于序列我 / 喜欢 / 机器学习 / 它注意力矩阵可以理解为我 喜欢 机器学习 它我 · · · ·喜欢 · · · ·机器学习 · · · ·它 · · 高 ·如果“它”这一行在“机器学习”这一列权重较高就说明模型在更新“它”的表示时重点参考了“机器学习”。从通俗角度看注意力矩阵就像一张“关注关系表”。它记录了每个 token 在理解自己时分别参考了其他 token 多少信息。需要注意注意力权重不是人类手工标注的语法关系。它是模型为了完成训练任务自动学习出来的计算权重。有时注意力图可以帮助理解模型行为但不能简单等同于人类语言学解释。六、多头自注意力从多个角度看上下文在 Transformer 中常用的不是单个自注意力而是多头自注意力Multi-Head Self-Attention。它的核心思想是让模型用多个不同的注意力头从不同角度学习 token 之间的关系。例如在一句话中一个注意力头可能关注主语和谓语关系另一个注意力头可能关注指代关系还有一个注意力头可能关注局部短语结构。图 3多头注意力与因果掩码从通俗角度看单头注意力像一个人只从一个角度读句子。多头注意力像多个专家同时读句子每个人关注不同线索最后把意见汇总起来。多头注意力可以表示为多个头的结果会拼接起来其中• head_i 表示第 i 个注意力头• h 表示注意力头数量• Concat 表示拼接• W_O 表示输出投影矩阵多头机制可以增强模型表达能力使模型同时捕捉多种上下文关系。七、自注意力与位置编码自注意力机制本身主要计算 token 之间的关系但它并不天然知道 token 的顺序。例如从纯自注意力角度看我喜欢你和你喜欢我如果没有位置信息模型很难知道二者顺序不同。因此Transformer 通常需要加入位置编码或位置嵌入。位置编码的作用是告诉模型每个 token 在序列中的位置。输入 Transformer 前Token Embedding 通常会与 Position Embedding 结合其中• E_token 表示 Token embedding• E_position 表示位置 Embedding• X 表示加入位置信息后的输入表示从通俗角度看• Token Embedding 告诉模型“这个词是什么”• Position Embedding 告诉模型“这个词在哪里”自注意力机制再根据这些表示计算 token 之间的关系。因此自注意力负责“谁和谁相关”位置编码负责“谁在什么位置”。二者配合Transformer 才能同时理解内容和顺序。八、自注意力的优势、局限与使用注意事项1、自注意力的主要优势自注意力最大的优势是可以直接建模全局关系。任意两个 token 之间都可以通过注意力权重建立联系不需要像 RNN 那样一步步传递。其次自注意力适合并行计算。在训练时一个序列中的多个位置可以同时计算这比按时间步顺序处理的 RNN 更适合大规模加速。再次自注意力具有较强的上下文建模能力。同一个词在不同上下文中可以得到不同表示。例如“苹果”在不同句子中可以表示水果也可以表示公司。从通俗角度看自注意力的优势在于它让模型可以根据上下文动态决定“当前应该重点看哪里”。2、自注意力的主要局限自注意力也有局限。首先标准自注意力的计算成本较高。如果序列长度为 L注意力矩阵大小为这意味着长文本会带来较大计算和显存压力。通常可以把标准注意力复杂度近似理解为其中• L 表示序列长度• O(L²) 表示计算量随序列长度平方级增长其次自注意力本身不包含顺序信息需要位置编码配合。再次注意力权重不一定等于可解释因果关系。某个 token 被高权重关注并不一定说明它就是人类理解中的唯一原因。3、使用自注意力时需要注意的问题使用自注意力时需要注意• Q、K、V 是由输入线性变换得到的• 注意力权重来自 Q 与 K 的相似度• Value 才是真正被加权汇总的信息• 多头注意力可以从多个角度建模关系• 自注意力需要位置编码补充顺序信息• 长序列会带来较高计算成本• 注意力图可以辅助理解但不能过度解释• 生成式模型中通常使用因果掩码避免看到未来 token最后一点尤其重要。在 GPT 类模型中当前位置只能关注自己和之前的 token不能偷看后面的 token。这种机制称为因果自注意力Causal Self-Attention。九、Python 示例下面给出几个简单示例用来帮助理解自注意力的基本计算。示例 1用 PyTorch 手写简化版自注意力import torchimport torch.nn.functional as F # 假设有 1 个 batch4 个 token每个 token 是 8 维向量X torch.randn(1, 4, 8) # 定义 Q、K、V 的线性变换矩阵可学习参数W_Q torch.randn(8, 8)W_K torch.randn(8, 8)W_V torch.randn(8, 8) # 线性变换得到查询、键、值矩阵Q X W_Q # (1,4,8)K X W_K # (1,4,8)V X W_V # (1,4,8) d_k K.shape[-1] # 键向量的维度用于缩放 # 计算注意力分数 Q·K^T / sqrt(d_k) 形状 (1,4,4)scores Q K.transpose(-2, -1) / (d_k ** 0.5) # 对最后一个维度序列内做 softmax得到注意力权重每行和为1attn_weights F.softmax(scores, dim-1) # (1,4,4) # 加权汇总 Value输出 attn_weights Voutput attn_weights V # (1,4,8) print(输入形状, X.shape) print(注意力权重形状, attn_weights.shape) print(输出形状, output.shape)输出形状通常为输入形状 torch.Size([1, 4, 8])注意力权重形状 torch.Size([1, 4, 4])输出形状 torch.Size([1, 4, 8])其中• 4 × 4 的注意力权重矩阵表示 4 个 token 两两之间的关注关系• 输出仍然是 4 个 token 的表示• 每个 token 的输出已经融合了上下文信息示例 2观察注意力矩阵import torchimport torch.nn.functional as F # 固定随机种子便于复现结果torch.manual_seed(0) # 输入1个序列长度4每个位置特征维度8X torch.randn(1, 4, 8) # 初始化Q、K、V的权重矩阵可学习参数W_Q torch.randn(8, 8)W_K torch.randn(8, 8)W_V torch.randn(8, 8) # 线性变换得到查询、键、值矩阵Q X W_Q # (1,4,8)K X W_K # (1,4,8)V X W_V # (1,4,8) # 计算注意力分数Q·K^T / sqrt(d_k)形状 (1,4,4)scores Q K.transpose(-2, -1) / (K.shape[-1] ** 0.5) # 对最后一个维度做 softmax得到注意力权重每行和为1attn_weights F.softmax(scores, dim-1) # 打印注意力权重矩阵第一行对应第一个查询对所有键的注意力分布print(attn_weights[0])输出是一个 4 × 4 矩阵。可以把它理解为第 1 行token 1 对所有 token 的关注比例第 2 行token 2 对所有 token 的关注比例第 3 行token 3 对所有 token 的关注比例第 4 行token 4 对所有 token 的关注比例每一行的数值加起来约等于 1。示例 3使用 PyTorch 的 MultiheadAttentionimport torchimport torch.nn as nn # 定义多头注意力层输入特征维度164个注意力头batch_firstTrue 表示输入形状为 (batch, seq, feature)attention nn.MultiheadAttention( embed_dim16, # 输入向量维度 num_heads4, # 并行注意力头数必须整除 embed_dim batch_firstTrue # 输入形状 (batch, seq_len, embed_dim)) # 生成一批随机输入2个序列每个序列5个位置每个位置16维特征x torch.randn(2, 5, 16) # 自注意力query、key、value 使用相同输入output, attn_weights attention( queryx, keyx, valuex) print(输出形状, output.shape) # (2,5,16)print(注意力权重形状, attn_weights.shape) # (2,5,5)输出形状通常为输出形状 torch.Size([2, 5, 16])注意力权重形状 torch.Size([2, 5, 5])这里 query、key、value 都来自同一个 x因此这是自注意力。如果 query 来自一个序列key 和 value 来自另一个序列则通常称为交叉注意力。示例 4因果掩码在生成式模型中当前位置不能看到未来 token。可以用上三角掩码实现import torch seq_len 5 # 序列长度 # 创建上三角掩码对角线以上为 True用于遮住未来位置因果注意力mask torch.triu( torch.ones(seq_len, seq_len), # 全1矩阵 diagonal1 # 从主对角线的上一行开始置True不含对角线).bool() # 转换为布尔类型 print(mask)输出类似tensor([[False, True, True, True, True], [False, False, True, True, True], [False, False, False, True, True], [False, False, False, False, True], [False, False, False, False, False]])这个掩码表示• 第 1 个 token 不能看后面的 token• 第 2 个 token 只能看第 1、2 个 token• 第 3 个 token 只能看第 1、2、3 个 token• 以此类推从通俗角度看因果掩码防止模型在生成时提前看到未来答案。 小结自注意力机制是一种让序列中每个 token 根据相关性主动参考其他 token 的方法。它通过 Q、K、V 计算注意力权重再对 Value 加权汇总得到融合上下文的新表示。多头自注意力可以从多个角度捕捉关系位置编码则补充顺序信息。对初学者而言可以把自注意力理解为模型在理解每个词时自动判断当前应该重点参考上下文中的哪些词。“点赞有美意赞赏是鼓励”