Vision Transformer
前言
虽然 Transformer 架构已成为自然语言处理任务的事实标准,但它在计算机视觉领域的应用仍然有限。在视觉领域,注意力要么与卷积网络结合使用,要么用来替换卷积网络的某些组件,同时保持其整体结构不变。论文中表明,这种对 CNN 的依赖是不必要的,直接应用于图像块序列的纯 Transformer 可以在图像分类任务中表现得非常好。当对大量数据进行预训练并转移到多个中型或小型图像识别基准(ImageNet、CIFAR-100、VTAB 等)时,与最先进的卷积网络相比,Vision Transformer (ViT) 取得了出色的结果,同时训练所需的计算资源却少得多。消融实验结果如下:
模型理解
Vision Transformer理解
上图是原论文中给出的关于Vision Transformer(ViT)的模型框架。,模型由三个模块组成:
- Linear Projection of Flattened Patches(Embedding层)
- Transformer Encoder(图右侧有给出更加详细的结构)(论文Attention Is All You Need中的结构)
- MLP Head(多层感知机头,最终用于分类的层结构)
Embedding层结构理解
Patch+Position Embedding的作用主要是对输入进来的图片进行分块处理,每隔一定的区域大小划分图片块。然后将划分后的图片块组合成序列。
论文中是使用卷积实现该操作。在VIT中,我们常设置这个卷积的卷积核大小为$16 \times 16$,步长也为16,卷积核个数为768。此时,卷积就会每隔16像素点对图片进行特征提取,图像块的特征提取就不会重叠。对于大小为$224 \times 224\times 3 $的图片而言,会生成一个$14\times 14\times 768$的特征层。
为什么这个操作实现了图像分块?
因为在$14 \times 14$的特征矩阵中,每一个$1\times 1$的格子中的数,代表的就是原图像中$16\times 16$像素的图像块的特征(卷积操作)。
下一步就是将这个特征层组合成序列,组合的方式非常简单,就是将高宽维度进行平铺,[14, 14, 768]在高宽维度平铺后,获得一个[196, 768]的特征层。平铺完成后,我们会在图片序列中添加上Cls Token,该Token会作为一个单位的序列信息一起进行特征提取,图中的这个0*就是Cls Token,我们此时获得一个197, 768的特征层。(Cls Token是concat到[196, 768]的特征层上的。)
[196, 768]的特征矩阵应该是什么样子?
结构概述
- 行数(197):这个矩阵的行数由两个部分组成:
- 1 行:
cls_token
,用于捕捉整个图像的全局特征。- 196 行:每个图像块的特征向量,表示图像被划分为 $16 \times 16 $的块后,提取的特征。
列数(768):每一行的特征维度是 768,通常与 Transformer 中的隐藏层维度相对应。
示例表示
假设
cls_token
和图像块特征都用随机值填充,那么矩阵的示例表示如下:
解释
- 第一行(
cls_token
):是一个向量,表示整个图像的全局信息,它的值会在训练过程中更新,以便更好地捕捉图像的特征。后196行(图像块特征):每一行对应一个图像块的特征,反映该块在图像中的局部信息。这些特征是通过卷积操作提取的,通常采用的是滑动窗口方法,对图像进行分块处理后得到。
使用位置嵌入
在输入到 Transformer 之前,这个矩阵通常还会与位置嵌入相加,以提供每个元素在序列中的位置信息。这可以帮助模型理解各个块之间的相对位置关系。
Cls Token的作用
Cls Token的查询向量也会与其他图像块的键向量进行点积。
如果 cls_token
的查询向量与某个图像块特征的键向量点积的结果较高,表示 cls_token
对该图像块特征的信息非常关注,这个图像块在整个图像中扮演了重
要角色。反之,较低的点积结果表示 cls_token
对该图像块的关注较少,可能这个图像块的信息对整体分类影响不大。
Transformer Encoder层结构理解
参考:1.Vision Transformer详解-CSDN博客
2.神经网络学习小记录67——Pytorch版 Vision Transformer(VIT)模型的复现详解_vit复现代码-CSDN博客
3.Transformer 模型详解_transformer模型-CSDN博客
MLP Head层结构理解
在 Vision Transformer (ViT) 中,MLP Head
是多层感知机(Multilayer Perceptron, MLP)用于最终的分类任务。它的主要功能是将 cls_token
的输出特征向量转换为最终的分类结果。
cls_token
的最终输出
经过 ViT 的多层 Transformer 处理后,cls_token
的特征被不断与图像块的特征交互,最终生成了一个表示全局图像信息的向量,形状为 B×768B \times 768B×768,其中:
- BBB 是批量大小。
- 768 是特征的维度(这是 Transformer 的输出维度)。
MLP Head 的结构
MLP Head
通常包括以下几层:
- 全连接层:将 768 维特征向量映射到类别数(如 1000 个类别),用线性变换处理。
- 激活函数:可能使用激活函数(如 ReLU 或 GELU),引入非线性。
- 输出层:另一个全连接层,最终输出分类 logits(未归一化的分类分数)。
具体来说,MLP Head
的结构通常如下:
1 | python class MLPHead(nn.Module): |
具体流程
假设我们使用 ViT 来分类图片,整个 MLP Head
的具体使用过程如下:
得到 cls_token
的特征
在 ViT 的前向传播过程中,经过自注意力机制的多层处理,cls_token
的输出是一个全局特征向量。假设其形状是 B×768B \times 768B×768(批量大小为 BBB,每个特征向量的维度为 768)。
1 | #cls_token 经过 transformer 输出 |
将 cls_token
输入 MLP Head
cls_token_output
作为 MLP Head
的输入,使用全连接层将其转换为分类的 logits。假设类别数为 1000,输出的形状为 $B \times 1000$,其中每个值表示对应类别的未归一化分数。
1 | # 经过 MLP Head |
分类和计算损失
- 在训练时,logits 通常会与真实标签进行比较,计算损失(例如交叉熵损失)。
- 在推理时,logits 会通过 Softmax 转换为类别概率,从而得到最终的分类结果。
1 | # 通过 Softmax 计算概率 |
MLP Head 的作用
MLP Head
的核心作用是通过全连接层将高维特征(768 维)转换为具体的类别预测结果。由于 cls_token
已经聚合了所有图像块的信息,它代表了全局图像的特征。MLP Head
只需要对这个全局特征进行处理,并将其映射到具体类别上。