首页
学习
活动
专区
圈层
工具
发布
社区首页 >专栏 >深度学习之一篇文章带你深度理解注意力机制

深度学习之一篇文章带你深度理解注意力机制

作者头像
阳光宅猿
发布2026-02-03 15:14:45
发布2026-02-03 15:14:45
1060
举报

导 语

在深度学习领域,注意力机制(Attention Mechanism)已经成为近年来最受瞩目的研究热点之一。它不仅提升了现有模型的性能,更启发了全新的网络结构,如Transformer模型。注意力机制被广泛应用于自然语言处理(NLP)、计算机视觉(CV)以及语音处理等领域。
1、什么是注意力机制?

要理解注意力机制,首先要了解其原理。注意力机制的灵感来自于人类的认知过程。当我们观察复杂场景时,视觉系统并不会同时处理所有信息,而是会选择性地关注某些重要部分。例如,当我们读一篇文章时,我们不会一次性记住每个单词,而是会根据上下文对某些单词给予更多关注。

机器学习中的注意力机制模仿了这一过程。在传统的序列模型(如RNN或LSTM 长短期记忆 (LSTM) 网络是一种特殊的循环神经网络 (RNN) )中,模型通常会处理整个输入序列,然后生成一个输出向量。然而,在这个过程中,模型可能会忽略某些重要的信息,尤其是对于较长的序列。注意力机制通过为每个输入元素分配一个权重,来帮助模型关注重要信息,从而生成更为有效的输出。

注意力机制主要有两个方面:

1、决定需要关注输入的哪部分

2、分配有限的信息处理资源给重要的部分

注意力机制的一种非正式的说法是,神经注意力机制可以使得神经网络具备专注于其输入(或特征)子集的能力:选择特定的输入。注意力可以应用于任何类型的输入而不管其形状如何。在计算能力有限情况下,注意力机制(attention mechanism)是解决信息超载问题的主要手段的一种资源分配方案,说白了就是将计算资源分配给更重要的任务

注意力一般分为两种:一种是自上而下的有意识的注意力,称为聚焦式(focus)注意力。聚焦式注意力是指有预定目的、依赖任务的、主动有意识地聚焦于某一对象的注意力;另一种是自下而上的无意识的注意力,称为基于显著性(saliency-based)的注意力。基于显著性的注意力是由外界刺激驱动的注意,不需要主动干预,也和任务无关。如果一个对象的刺激信息不同于其周围信息,一种无意识的“赢者通吃”(winner-take-all)或者门控(gating)机制就可以把注意力转向这个对象。不管这些注意力是有意还是无意,大部分的人脑活动都需要依赖注意力,比如记忆信息,阅读或思考等。

关注公众号【阳光宅猿】回复【AIGC】领取最新AI人工智能学习资料,包含RAG、Agent、深度学习、模型微调等多种最新技术文档!

关注公众号【阳光宅猿】回复【加群】进入大模型技术交流群一起学习成长!!!

在认知神经学中,注意力是一种人类不可或缺的复杂认知功能,指人可以在关注一些信息的同时忽略另一些信息的选择能力。在日常生活中,我们通过视觉、听觉、触觉等方式接收大量的感觉输入。但是我们的人脑可以在这些外界的信息轰炸中还能有条不紊地工作,是因为人脑可以有意或无意地从这些大量输入信息中选择小部分的有用信息来重点处理,并忽略其他信息。这种能力就叫做注意力。注意力可以体现为外部的刺激(听觉、视觉、味觉等),也可以体现为内部的意识(思考、回忆等)

Attention机制是深度学习中的一种技术,特别是在自然语言处理和计算机视觉领域中得到了广泛的应用。它的核心思想是模仿人类的注意力机制,即人类在处理信息时会集中注意力在某些关键部分上,而忽略其他不那么重要的信息。在机器学习模型中,这可以帮助模型更好地捕捉到输入数据中的关键信息。

基本公式

注意力机制的核心公式可以表示为:

Query (Q):查询向量,代表了需要聚焦的输入部分。

Key (K): 键向量,表示输入序列中的每个元素。

Value (V): 值向量,表示需要提取的信息。

(d_k): 键向量的维度,常用于缩放处理,避免内积结果过大。

注意力机制的原理架构图如图所示,后面我也会通过代码进行演示说明:

1.png
1.png

注意力机制的作用就是,根据解码器的“查询”(外部信息),去“关注”编码器隐藏状态(外部信息源)中哪些部分最重要,然后加权汇总成一个“上下文向量”。

简单比喻:你在翻译一句话(解码),遇到一个动词,你不确定它的意思,于是你回头去查阅原文(编码器输出)中相关部分。你的“疑问”是外部的查询,引导你去关注原文的特定位置。

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

传统的RNN和LSTM结构虽然能处理序列数据,但在处理较长的序列时,容易出现信息遗忘问题(如梯度消失)注意力机制通过为每个输入位置计算不同的权重,使模型能够动态地关注特定位置的输入,从而有效缓解序列长度对模型性能的影响。

例如,在机器翻译任务中,目标是将一个句子从源语言翻译为目标语言。在经典的Seq2Seq模型(Seq2Seq模型是一种序列到序列的模型,由两个RNN组成:编码器(Encoder)和解码器(Decoder))中,编码器会对整个源句子进行编码,然后解码器基于这一编码生成目标句子。然而,对于长句子来说,模型很容易在解码过程中丢失重要的上下文信息。通过加入注意力机制,解码器可以根据当前的翻译位置动态选择源句子中的相关部分,从而生成更准确的翻译。

我也用Python实现了这种经典的翻译模型,需要代码的可以后台私信我,已经写好相关注解,通俗易懂。需要的私我。

3. 注意力机制的应用场景

随着注意力机制的提出和发展,它已经在许多领域中得到了广泛应用。以下是几个主要的应用场景:

1 自然语言处理

注意力机制最初在自然语言处理领域得到了广泛应用。它被用来解决序列到序列(Seq2Seq)模型中的信息遗失问题。例如,在机器翻译任务中,注意力机制帮助模型在生成每个目标词时动态选择源句子中最相关的部分。

此外,注意力机制在文本摘要、对话生成、问题回答等任务中也起到了重要作用。例如,Transformer模型的引入彻底改变了NLP领域,它通过完全抛弃RNN结构,依赖注意力机制实现了极大的性能提升。

2 计算机视觉

在计算机视觉领域,注意力机制被广泛应用于图像识别、目标检测和图像生成等任务。例如,在目标检测任务中,注意力机制可以帮助模型专注于图像中最相关的区域,从而更准确地检测目标。

经典的卷积神经网络(CNN)虽然能有效处理图像数据,但由于卷积核的局限性,它在处理全局依赖关系时表现较差。注意力机制的引入,让模型能够在全局范围内选择性地关注图像中的某些区域,从而提升了识别效果。

3 语音处理

在语音识别和语音生成任务中,注意力机制也被广泛应用。尤其是在语音生成中,注意力机制帮助模型聚焦于不同的时间帧,从而生成更为流畅的语音信号。例如,基于Transformer的语音识别系统,已经在许多任务中取得了领先的效果。

4. 注意力机制的实现与问题探究

基本的注意力机制通常用于经典的序列到序列模型中,最早应用于机器翻译任务。在这种机制中,输入序列中的每个元素(即词向量)都会被赋予一个权重,这些权重表示模型在生成输出时对该元素的关注程度。通过加权求和,模型能够动态地聚焦于输入序列中最相关的信息。所以我将从两个代码示例出发,一个是基础的注意力机制,明白其原理,一个是实战训练出来一个真正的STS翻译模型。

关注公众号【阳光宅猿】回复【AIGC】领取最新AI人工智能学习资料,包含RAG、Agent、深度学习、模型微调等多种最新技术文档!

关注公众号【阳光宅猿】回复【加群】进入大模型技术交流群一起学习成长!!!

实现简单的注意力机制

为了帮助理解注意力机制的工作原理,下面我们将实现一个简单的注意力机制模型。该模型会对输入序列中的每个元素进行加权,然后根据权重对序列进行加权求和,生成最终的输出。

代码语言:javascript
复制
# 1. 导入PyTorch核心库,是所有PyTorch代码的基础
import torch
# 2. 导入PyTorch的神经网络模块,用于构建层和模型
import torch.nn as nn
# 3. 导入PyTorch的函数模块,包含激活函数、损失函数等常用函数
import torch.nn.functional as F
# 4. 定义一个简单的注意力机制类,继承自nn.Module(所有PyTorch模型的基类)
class SimpleAttention(nn.Module):
    # 5. 初始化函数,input_dim是输入特征的维度(比如每个时间步的向量长度)
    def __init__(self, input_dim):
        # 6. 必须调用父类的初始化函数,这是PyTorch自定义模型的固定写法
        super(SimpleAttention, self).__init__()
        # 7. 定义线性层:将输入维度(input_dim)映射为1维(每个位置的注意力分数)
        #    作用:计算每个序列位置的"重要性分数"
        self.attention = nn.Linear(input_dim, 1)
    # 8. 前向传播函数(模型的核心逻辑,定义数据如何通过模型)
    def forward(self, x):
        # 9. 打印输入形状(可选,方便新手理解输入维度)
        #    x 的形状:(batch_size, seq_len, input_dim)
        #    batch_size:批次大小(一次处理多少条数据)
        #    seq_len:序列长度(比如句子的单词数)
        #    input_dim:每个序列位置的特征维度
        print(f"输入x的形状: {x.shape}")

        # 10. 第一步:通过线性层计算原始注意力分数
        #     输出形状:(batch_size, seq_len, 1)
        raw_attn_scores = self.attention(x)

        # 11. 第二步:用softmax函数归一化注意力分数
        #     dim=1:在seq_len维度上归一化,保证每个序列的注意力权重之和为1
        #     输出形状:(batch_size, seq_len, 1)
        attn_weights = F.softmax(raw_attn_scores, dim=1)

        # 12. 第三步:根据注意力权重对输入进行加权求和
        #     attn_weights * x:逐元素相乘,形状保持(batch_size, seq_len, input_dim)
        #     torch.sum(..., dim=1):在seq_len维度求和,最终得到(batch_size, input_dim)
        weighted_sum = torch.sum(attn_weights * x, dim=1)

        # 13. 返回加权后的输出向量和注意力权重(方便查看每个位置的权重)
        return weighted_sum, attn_weights
# 14. 构造测试输入数据(模拟实际场景的输入)
batch_size = 3    # 一次处理3条数据
seq_len = 5       # 每条数据的序列长度为5
input_dim = 4     # 每个序列位置的特征维度为4
# 生成随机张量,值在0~1之间,形状为(3,5,4),模拟批量的序列数据
x = torch.rand(batch_size, seq_len, input_dim)
# 15. 初始化注意力模型,传入输入特征维度4
model = SimpleAttention(input_dim)
# 16. 前向传播:将输入数据传入模型,得到输出和注意力权重
output, attention_weights = model(x)
# 17. 打印输出向量(形状:(3,4),每个批次样本对应一个加权后的向量)
print("输出向量:", output)
# 18. 打印注意力权重(形状:(3,5,1),每个样本的5个序列位置各有一个权重)
print("注意力权重:", attention_weights)

输出结果为

代码语言:javascript
复制
输入x的形状: torch.Size([3, 5, 4])
输出向量: tensor([[0.5850, 0.5156, 0.2812, 0.2477],
        [0.4798, 0.5979, 0.3718, 0.4623],
        [0.6567, 0.3200, 0.3939, 0.5630]], grad_fn=<SumBackward1>)
注意力权重: tensor([[[0.2110],
         [0.2185],
         [0.1941],
         [0.1600],
         [0.2163]],

        [[0.2044],
         [0.2101],
         [0.1972],
         [0.1894],
         [0.1989]],

        [[0.2004],
         [0.2069],
         [0.2069],
         [0.2173],
         [0.1685]]], grad_fn=<SoftmaxBackward0>)

根据这个注意力机制的输出,张量形状 `[3, 5, 4]` 中各维度的含义如下:

- 3:表示批次大小(batch size),即同时处理的样本数量。这里有3个不同的输入样本

- 5:表示序列长度(sequence length),即每个样本中的时间步或位置数。每个样本包含5个位置的元素

- 4:表示特征维度(feature dimension),即每个位置的特征向量维度。每个位置有4维的特征向量

从输出结果可以看出:

- 输出向量形状为 `[3, 4]`(经过对序列维度求和)

- 注意力权重形状为 `[3, 5, 1]`(每个样本在每个位置上的注意力分数)

这是典型的Transformer模型中自注意力层的结构,其中批次中的每个样本都会与自身的序列进行注意力计算。

思考: 为什么不能将self.attention = nn.Linear(input_dim, 1)中的1改为2呢?

注意力分数的本质:

nn.Linear(input_dim, 1) 线性层为序列中的每个位置计算一个单一的数值(注意力分数),这个分数表示该位置在整个序列中的相对重要性

后续处理步骤:

raw_attn_scores = self.attention(x) 输出形状为 (batch_size, seq_len, 1)

F.softmax(raw_attn_scores, dim=1) 在序列长度维度上应用softmax,使所有位置的分数总和为1并使用这些权重对原输入进行加权求和

如果改为2会发生什么:

输出形状变为 (batch_size, seq_len, 2),意味着每个位置有两个注意力分数这违反了注意力机制的基本原理:我们只需要一个权重值来表示每个位置的重要性。且Softmax操作无法正确归一化(因为需要确保所有位置的权重总和为1)

注意力机制的目标是产生一个概率分布,让模型能够"关注"输入序列中最重要的部分,概率分布必须是一维的(每个位置一个权重值),且总和为1。因此,nn.Linear(input_dim, 1) 中的 1 是固定的,它对应于为每个序列位置生成单个注意力权重值的需求。

思考:forward前向传播函数做了什么?

forward前向传播函数是 PyTorch 模型的核心逻辑入口,它定义了输入数据如何通过模型的各个组件(层 / 运算)转化为输出—— 不是被动 “往每个层传播”,而是主动规定数据的 “流动路径” 和 “运算规则”。

打个比方:把模型比作工厂,forward函数就是工厂的 “生产流程单”,明确了原材料(输入数据)要经过哪些机器(层)、按什么顺序加工,最终产出成品(输出结果)。

那代码里的 forward 函数的数据流动路径是:

输入x → 线性层(self.attention)→ softmax归一化 → 加权求和 →输出

思考:为啥要有第三步根据注意力权重对输入进行加权求和?不进行加权求和不行吗?

加权求和的作用

1. 聚合信息:

- 应用注意力权重后,重要的位置会获得更高的权重

- 不重要的位置会获得较低的权重

- 通过加权求和,模型能够聚焦于最相关的输入信息

2. 创建上下文向量:

- 加权求和的结果是一个固定大小的向量(形状:`[batch_size, input_dim]`)

- 这个向量包含了整个序列的信息,但更强调重要的部分

- 可以作为后续任务的输入(如分类、解码等)

3. 实现选择性关注:

- 没有加权求和,就只是得到了注意力权重,但并未利用这些权重来影响实际的数据流

- 加权求和才是真正实现"关注重要信息,忽略不重要信息"的关键步骤

如果不进行加权求和,只保留注意力权重,那么:

1. 丢失原始信息:你只有每个位置的权重,但没有经过这些权重过滤的特征信息

2. 无法用于下游任务:后续的神经网络层需要有意义的特征向量,而不是单纯的权重值

3. 失去注意力机制的意义:注意力机制的目的就是让模型能够动态地关注输入的不同部分,这需要通过加权求和来实现

关注公众号【阳光宅猿】回复【AIGC】领取最新AI人工智能学习资料,包含RAG、Agent、深度学习、模型微调等多种最新技术文档!

关注公众号【阳光宅猿】回复【加群】进入大模型技术交流群一起学习成长!!!

因此我们明白了上面原理图的整体流程,注意力机制的工作流程简单总结就是:

1. 计算注意力分数:

通过线性层计算原始注意力分数,确定每个位置的重要程度,其实在我们模型日常中就是将自然语言进行高维空间向量化Embedding,捕捉输入的语义信息,并给每个词向量进行打分。

2. 应用Softmax:将分数转换为概率分布(权重总和为1)

3. 加权求和:根据权重重新组合输入特征,突出重要信息

这三步共同构成了完整的注意力机制,缺一不可。加权求和是将注意力权重转化为实际特征表示的关键步骤,让模型学会关注输入中最相关的部分。

经过上面的代码,我又引申出了,如何采用注意力机制实现经典的Seq2Seq模型,将源语言翻译成目标语言,经过我不断的摸索,终于成功复现,由于代码量过长,并且注释也多,我就不往这上面粘贴了,需要的可以后台私信我,我将代码发给你。训练结果如下:

结语:

好久没有更新公众号了,忙着带娃,忙着工作,沉下心去搞点干货的时间显得弥足珍贵,那就从注意力机制开始吧,我将重点整理一些深度学习的相关机制原理文章,一是自我学习,二是加深对底层知识的理解,更好的掌握主流模型,便于后续工作中更好的使用和训练模型。最近看到了一句名言,蛮有感触的,“What I can not create I do not understand.” 这句话是物理大师费曼所说,“凡我不能创造的,我就不能理解” 正中我眉心,因此我抽出一些时间来进行填补和学习。

我们创建了一个大模型技术交流群,便于在日常能够和大家一起学习交流,捕捉行业动态,大家可以加我或直接加群:

本文参与 腾讯云自媒体同步曝光计划,分享自微信公众号。
原始发表:2026-01-23,如有侵权请联系 cloudcommunity@tencent.com 删除

本文分享自 阳光宅猿 微信公众号,前往查看

如有侵权,请联系 cloudcommunity@tencent.com 删除。

本文参与 腾讯云自媒体同步曝光计划  ,欢迎热爱写作的你一起参与!

评论
登录后参与评论
0 条评论
热度
最新
推荐阅读
目录
  • 在深度学习领域,注意力机制(Attention Mechanism)已经成为近年来最受瞩目的研究热点之一。它不仅提升了现有模型的性能,更启发了全新的网络结构,如Transformer模型。注意力机制被广泛应用于自然语言处理(NLP)、计算机视觉(CV)以及语音处理等领域。
    • 1、什么是注意力机制?
    • 基本公式
    • 2 、为什么需要注意力机制?
    • 3. 注意力机制的应用场景
    • 1 自然语言处理
    • 2 计算机视觉
    • 3 语音处理
    • 实现简单的注意力机制
  • 那代码里的 forward 函数的数据流动路径是:
领券
问题归档专栏文章快讯文章归档关键词归档开发者手册归档开发者手册 Section 归档