Transformer在目标检测的几篇论文

Transformer在目标检测的几篇论文

blog记录最近看的两篇文章

如果你了解第二篇文章,那么第三篇文章就相对容易。

前置废话

       最近看了几篇文章,姑且记录下来。最近Transformer在视觉上的paper不断增多,各种idea层出不穷,如swin transformer等。但一切都有迹可循。本blog记录关于目标检测两篇比较有代表性的paper。

前置知识

  • 了解最原始的Transformer,
  • 优化分配问题(匈牙利法)。

这里简述关于这两点知识。

Transformer

SelfAttetion

       对于给定的Feature Map x ∈ R c × h × w x \in R^{c\times h \times w} xRc×h×w, 不妨设置得到的 Q Q Q, K K K V V V都是相同维度,即 Q , K , V ∈ R c × h × w Q,K,V \in R^{c\times h \times w} Q,K,VRc×h×w.将 Q , K , V Q,K,V Q,K,V分别 r e s h a p e reshape reshape R h w × c R^{hw\times c} Rhw×c,那么 S A = Q K T SA = QK^{T} SA=QKT,进一步做归一化,可以得到
S A = s o f t m a x ( Q K T d k ) SA = softmax(\frac{QK^{T}}{\sqrt{d_{k}}}) SA=softmax(dk QKT) 最终得到的输出
A t t e n t i o n ( Q , K , V ) = s o f t m a x ( Q K T d k ) V                   ( 1 ) Attention(Q,K,V) = softmax(\frac{QK^{T}}{\sqrt{d_{k}}})V \ \ \ \ \ \ \ \ \ \ \ \ \ \ \ \ \ (1) Attention(Q,K,V)=softmax(dk QKT)V                 (1)
可以看到 S A ∈ R h w × h w SA \in R^{hw\times hw} SARhw×hw, A t t e n t i o n ( Q , K , V ) ∈ R h w × c Attention(Q,K,V) \in R^{hw \times c} Attention(Q,K,V)Rhw×c,这就是想要的结果.
       Multi-head机制只是把通道数拆成多份,如 m m m份,那么上述的shape就变成了 Q , K , V ∈ R h × w × c m Q,K,V\in R^{h\times w\times \frac{c}{m}} Q,K,VRh×w×mc,最后将m个head进行 c o n c a t concat concat,得到 A t t e n t i o n ∈ R h w × c Attention\in R^{hw\times c} AttentionRhw×c . c r o s s − a t t e t i o n cross-attetion crossattetion和这个类似,只不过 K K K V V V的来源不同而已,这里不再过多的赘述。

Position Embedding

        由于在self-attention的过程中,只考虑了两两之间的attention,这其实还不够,因为现实生活中位置对于特征也非常重要,原论文采用了两种方式进行position位置的编码。

  • hard coding(sin,cos函数编码)
  • position learning

对于hard coding的方式主要参考
P E ( p o s , 2 i ) = s i n ( p o s 1000 0 2 i / d m o d e l )              ( 2 ) PE(pos,2i)=sin(\frac{pos}{10000^{2i/d_{model}}}) \ \ \ \ \ \ \ \ \ \ \ \ (2) PE(pos,2i)=sin(100002i/dmodelpos)            (2)
P E ( p o s , 2 i + 1 ) = c o s ( p o s 1000 0 2 i / d m o d e l )              ( 3 ) PE(pos,2i+1)=cos(\frac{pos}{10000^{2i/d_{model}}}) \ \ \ \ \ \ \ \ \ \ \ \ (3) PE(pos,2i+1)=cos(100002i/dmodelpos)            (3)

对于position learning,本质上就把位置看作一个可学习的向量,通过网络不断的去学习,具体以
P E = E m b e d d i n g ( s e q l e n g t h , d m o d e l )              ( 4 ) PE = Embedding(seqlength, d_{model}) \ \ \ \ \ \ \ \ \ \ \ \ (4) PE=Embedding(seqlength,dmodel)            (4)

匈牙利法

        本质上,匈牙利法主要是求解最优化问题中的分配问题的,比如常见分配问题有运输问题。简单以一个记号表示,不妨设图 G = ( V 1 , V 2 , W ) G=(V_{1},V_{2},W) G=(V1,V2,W)来表示分配问题,其中 V 1 V_{1} V1表示 A A A地的 n n n点, V 2 V_{2} V2表示 B B B地的 m m m点, W W W表示 A A A地每个点到 B B B地每个点的代价,现在需要安排从A地到B地的最小代价匹配(一旦确定了某个配对关系,那么其他点就不能和该点进行配对了)。此时代价矩阵 W W W可表示为:
W = [ w 11 w 12 . . . w 1 m w 21 w 22 . . . w 2 m . . . . . . . . . . . . w n 1 w n 2 . . . w n m ] W=\left[ \begin{matrix} w_{11} & w_{12} & ... & w_{1m}\\ w_{21} & w_{22} & ... & w_{2m} \\ ... & ... & ... & ... \\ w_{n1} & w_{n2} & ...& w_{nm} & \end{matrix} \right] W=w11w21...wn1w12w22...wn2............w1mw2m...wnm

不妨设 x i j x_{ij} xij A A A地中的 i i i点分配给 B B B地的 j j j点, 那么该问题变成了一个最优化问题,表示方式如下:
min ⁡ z = ∑ i = 1 n ∑ j = 1 j = M w i j x i j \min z = \sum_{i=1}^{n}\sum_{j=1}^{j=M}w_{ij}x_{ij} minz=i=1nj=1j=Mwijxij
s . t .           ∑ i = 1 n x i j = 1 s.t. \ \ \ \ \ \ \ \ \ \sum_{i=1}^{n}x_{ij}=1 s.t.         i=1nxij=1
                    ∑ j = 1 m x i j = 1 \ \ \ \ \ \ \ \ \ \ \ \ \ \ \ \ \ \ \ \sum_{j=1}^{m}x_{ij}=1                    j=1mxij=1
                          x i j = 0     o r       1 \ \ \ \ \ \ \ \ \ \ \ \ \ \ \ \ \ \ \ \ \ \ \ \ \ x_{ij}=0 \ \ \ or \ \ \ \ \ 1                          xij=0   or     1

显然该问题可解。具体的解法有很多,但以匈牙利法为一类方法的代表,这里不过多描述该解法,只描述什么问题可以使用匈牙利法去求解。
       如果感兴趣可以参考运筹学的相关书籍。或者参考该blog匈牙利解法

DETR

DETR的网络和Transformer类似,它去掉了Transformer中Decoder部分计算self-Attention的Mask的部分,这是因为在图片中对于像素来说上下文是可知的,并不像自然语言处理处理句子中,进行预测的时候,当前只知道预测词之前的所有单词,对于之后的单词,并不知道,所以Transformer中进行softmax之前要进行一步mask。另外还有一点是position部分,在Transformer中,position embedding仅加在了词向量后,而DETR则是在所有输出的Attention部分都加上了position embedding.这一点可以从给出的网络图中可以看出,
请添加图片描述

注意这里的position encoding都加到每层计算attention中去了。文章中还针对在开始位置加postion encoding还是全部都加position encoding做了消融实验,实验结果是在每次计算attention的时候都加上效果最好。

另外DETR改进了原始Transformer不适用于做目标检测的部分。这部分主要体现在decoding部分,如下图。

上图中左图为DETR的结构,右图为Transformer的原始结构。可以清楚的看到不同点是

  • DETR将Transformer中Decoder部分的输入outputs(shift right)改成Object queries,这是因为在图像中不需要通过前一个词去预测后一个词(也就是shifted right).此外这个Object queries也不是什么神奇的东西,只是一个随机的参数(这里可以改进),这里从论文附录给的代码可以看出。
    请添加图片描述

  • 为完成目标检测任务,类比Faster-RCNN等网络,那么输出网络改成两个分支,一个bbox预测,一个类别预测。这里的网络也只是一个前馈神经网络。

那么DETR改进Transformer部分就完成了,但是,这里还有一个问题没有解决,那就是如何让预测与标签相对应,之前的Faster-RCNN等,不管是一阶段还是二阶段的做法是通过计算IOU的值来让预测的样本与GroundTruth进行匹配。这样做当然没问题,但是会增加计算的时间复杂度,因为会有很多框(RPN网络)。这里作者就提出了不使用这种方式,使用匈牙利法进行强制匹配,这样免去了计算IOU以及NMS的计算。
下面介绍如何完成这个匹配:
不妨设 P r e d i c t i o n Prediction Prediction ( P _ b b o x j , P _ c j ) (P\_bbox_{j},P\_c_{j}) (P_bboxj,P_cj), L a b e l Label Label ( L _ b b o x i , L _ c i ) (L\_bbox_{i},L\_c_{i}) (L_bboxi,L_ci)为对应的bounding box预测和分类结果。其中 i = 1 , 2 , ⋯ n i=1,2, \cdots n i=1,2,n, j = 1 , 2 , ⋯ m j=1,2, \cdots m j=1,2,m.此外 对于一副图像来说,那么图像中的目标应该来说不多,因此这里有 m > n m>n m>n.
当前我们不知道哪一个预测框对应的哪一个ground Truth,因此没办法计算loss. 现在类比我们的运输问题,想象一下把 P r e d i c t i o n Prediction Prediction看成是 A A A地, L a b e l Label Label看成是 B B B地,现在我们需要构建 P r e d i c t i o n Prediction Prediction L a b e l Label Label的代价函数,然后使用匈牙利法去求解完成这个匹配的最小代价,这样就可以知道 L a b e l Label Label中的第 i i i个对应的 P r e d i c t i o n Prediction Prediction j j j个。那么如何构建这个代价函数呢?很自然的通过 b o u n d i n g b o x bounding box boundingbox c l a s s class class来对应,代价函数为 W W W,
W = [ w 11 w 12 . . . w 1 m w 21 w 22 . . . w 2 m . . . . . . . . . . . . w n 1 w n 2 . . . w n m ] W=\left[ \begin{matrix} w_{11} & w_{12} & ... & w_{1m}\\ w_{21} & w_{22} & ... & w_{2m} \\ ... & ... & ... & ... \\ w_{n1} & w_{n2} & ...& w_{nm} & \end{matrix} \right] W=w11w21...wn1w12w22...wn2............w1mw2m...wnm
where w i j = ∥ P _ b b o x j − L _ b b o x i ∥ + ( − 1 ) P _ c j ( L _ c i ) w_{ij}=\|P\_bbox_{j}-L\_bbox_{i} \| + (-1)P\_c_{j}(L\_c_{i}) wij=P_bboxjL_bboxi+(1)P_cj(L_ci)
当然这里面是示意, ∥ P _ b b o x j − L _ b b o x i ∥ \|P\_bbox_{j}-L\_bbox_{i} \| P_bboxjL_bboxi好理解, P _ c j ( L _ c i ) P\_c_{j}(L\_c_{i}) P_cj(L_ci) 表示输出prediction的类别概率分布取第 L _ c j L\_c_{j} L_cj类别的数值。
有了这个代价函数,就可以得到Label中的第 i i i个,对应 P r e d i c t i o n Prediction Prediction中的 j = σ ( i ) j=\sigma(i) j=σ(i)。为了更好的理解,由于 m > n m>n m>n,因此扩展 m − n m-n mn个空类( ϕ \phi ϕ)或者称之为背景给Label,让其与 P r e d i c t i o n Prediction Prediction进行对应起来。
那么就有下图的对应关系。

请添加图片描述
至于空类( ϕ \phi ϕ)之前预测bounding box的值不重要,计算的时候,也不需要知道该值,这里可以不用显示指出。这样就知道了Label与Prediction之前的一一对应关系。知道了这个关系就可以计算loss函数了。

这里作者定义了一个Hungarian loss,类似计算代价函数,只不过把计算代价矩阵的classfication直接取值改成了交叉熵的形式,并且扩展到空类( ϕ \phi ϕ)也要计算损失,而bounding box的计算外加了一个iou loss。
L H u n g a r i a n ( y , y ^ ) = ∑ i = 1 N [ − l o g   p ^ σ ( i ) ^ ( c i ) + 1 c i ≠ ϕ L b o x ( b i , b σ ( i ) ^ ) ]     ( 5 ) L_{Hungarian}(y,\hat{y})=\sum^{N}_{i=1}[-log{\ \hat{p}_{\hat{\sigma(i)}}}(c_{i})+\mathscr{1}_{c_{i}\neq \phi}L_{box}(b_{i},\hat{b_{{\sigma(i)}}})] \ \ \ (5) LHungarian(y,y^)=i=1N[log p^σ(i)^(ci)+1ci=ϕLbox(bi,bσ(i)^)]   (5)
至此,DETR部分基本完成,当然里面有很多细节,可以参考原论文。

DETR的缺点。
  • 时间复杂度高。在Transformer中计算注意力时,也就是公式1,计算复杂度为 O ( H 2 W 2 C ) O(H^{2}W^{2}C) O(H2W2C),对图像来说,这个时间复杂度很高。
  • 模型预测小目标能力差。这个在原论文中有实验表明。

在论述Deformable DETR之前,如果你了解Deformable CNN,那么对你了解Deformable DETR有很大的帮助

Deformable CNN

关于这篇文章只介绍与CNN相关的部分,因为Deformable DETR只涉及到这部分的内容。pooling 部分可以参考原论文。
借用原论文的一张图可以很好的解释Deformable CNN.请添加图片描述
传统的CNN都是以固定的pattern进行点乘累加,用数学语言来表示就是,
以卷积核kernel_size = 3为例,定义 R = { ( − 1 , − 1 ) , ( − 1 , 0 ) , … , ( 1 , 1 ) } R =\{(-1,-1),(-1,0),\dots , (1,1)\} R={(1,1),(1,0),,(1,1)},对于Feature Map中第 l l l层每个位置 p 0 p_{0} p0,有 l + 1 l+1 l+1层的输出为:
y l + 1 ( p 0 ) = ∑ p n ∈ R w ( p n ) x l ( p 0 + p n ) y^{l+1}(p_{0})=\sum_{p_{n}\in R}{w(p_{n})x^{l}(p_{0}+p_{n})} yl+1(p0)=pnRw(pn)xl(p0+pn)
Deformable CNN不再以固定的pattern进行点乘累加,而是通过学习来找到应该与哪个位置相关,这样有利于相关特征的选区和扩展可视野。相比于传统的CNN,Deformable加入了可学习的位置参数 Δ p n \Delta{p_{n}} Δpn,数学表达式为:
y l + 1 ( p 0 ) = ∑ p n ∈ R w ( p n ) x l ( p 0 + p n + Δ p n )         ( 6 ) y^{l+1}(p_{0})=\sum_{p_{n}\in R}{w(p_{n})x^{l}(p_{0}+p_{n}+\Delta{p_{n}})} \ \ \ \ \ \ \ (6) yl+1(p0)=pnRw(pn)xl(p0+pn+Δpn)       (6)
那么具体的操作用原论文的图表示:请添加图片描述
这部分在代码实现和公式(6)是相反的过程,不是通过操作卷积核来实现,而是通过采样原图的间接方式实现,可以达到相同的效果。具体以下图的方式进行表示
CNN                                                                                                                 CNN
请添加图片描述
                                                                                                                Deformable CNN
Deformable CNN图中Offsets是偏离中心位置有多少的. Offsets是比Feature Map的通道数的两倍,这是因为偏移位置有两个方向,一个x轴一个y轴。当然Offsets里面的值不可能都是整数,可以对其进行双线性插值取值得到新的Feature Map,也就是Sampling.我这里为了方便,将feature map的通道数变为1,而Offsets通道应该是2,我组合放在了一起。可以看到首先进行的在offsets的基础上进行采样,而卷积核的数值和位置不做任何变换,这样可以得到Deformable CNN的形式

  • 3
    点赞
  • 30
    收藏
    觉得还不错? 一键收藏
  • 0
    评论
Transformer发轫于NLP(自然语言处理),并跨界应用到CV(计算机视觉)领域。 Swin Transformer是基于Transformer计算机视觉骨干网,在图像分类、目标检测、实例分割、语义分割等多项下游CV应用中取得了SOTA的性能。该项工作也获得了ICCV 2021顶会最佳论文奖。 本课程将手把手地教大家使用labelImg标注和使用Swin Transformer训练自己的数据集。  本课程将介绍Transformer及在CV领域的应用、Swin Transformer的原理。 课程以多目标检测(足球和梅西同时检测)为例进行Swin Transformer实战演示。 课程在Windows和Ubuntu系统上分别做项目演示。包括:安装软件环境、安装Pytorch、安装Swin-Transformer-Object-Detection、标注自己的数据集、准备自己的数据集(自动划分训练集和验证集)、数据集格式转换(Python脚本完成)、修改配置文件、训练自己的数据集、测试训练出的网络模型、性能统计、日志分析。  相关课程: 《Transformer原理与代码精讲(PyTorch)》https://edu.csdn.net/course/detail/36697《Transformer原理与代码精讲(TensorFlow)》https://edu.csdn.net/course/detail/36699《ViT(Vision Transformer)原理与代码精讲》https://edu.csdn.net/course/detail/36719《DETR原理与代码精讲》https://edu.csdn.net/course/detail/36768《Swin Transformer实战目标检测:训练自己的数据集》https://edu.csdn.net/course/detail/36585《Swin Transformer实战实例分割:训练自己的数据集》https://edu.csdn.net/course/detail/36586《Swin Transformer原理与代码精讲》 https://download.csdn.net/course/detail/37045
基于Transformer目标检测算法是近年来发展起来的一种新型目标检测算法。其主要思想是将Transformer模型应用于目标检测任务中,通过对图像中的不同位置进行编码和解码,实现对目标的检测和定位。以下是两篇相关论文的简要介绍和代码实现: 1. 结构重新设计 Rethinking Transformer-based Set Prediction for Object Detection(ICCV 2021) 该论文提出了一种新的Transformer-based目标检测算法,称为Transformer Set Prediction(TSP)。TSP通过重新设计Transformer的结构,将其应用于目标检测任务中。具体来说,TSP将输入图像分成多个子区域,并将每个子区域表示为一个向量。然后,TSP使用Transformer模型对这些向量进行编码和解码,以实现对目标的检测和定位。相比于传统的目标检测算法,TSP具有更好的性能和更高的效率。 以下是TSP的代码实现: ```python import torch import torch.nn as nn import torch.nn.functional as F class TSP(nn.Module): def __init__(self, input_dim, hidden_dim, num_heads, num_layers): super(TSP, self).__init__() self.input_dim = input_dim self.hidden_dim = hidden_dim self.num_heads = num_heads self.num_layers = num_layers self.encoder_layer = nn.TransformerEncoderLayer(d_model=input_dim, nhead=num_heads, dim_feedforward=hidden_dim) self.encoder = nn.TransformerEncoder(encoder_layer=self.encoder_layer, num_layers=num_layers) self.decoder_layer = nn.TransformerDecoderLayer(d_model=input_dim, nhead=num_heads, dim_feedforward=hidden_dim) self.decoder = nn.TransformerDecoder(decoder_layer=self.decoder_layer, num_layers=num_layers) self.linear = nn.Linear(input_dim, 1) def forward(self, x): x = x.permute(0, 3, 1, 2) # 将输入的图像转换为(batch_size, input_dim, height, width)的形式 x = x.reshape(x.shape[0], x.shape[1], -1) # 将图像分成多个子区域,并将每个子区域表示为一个向量 x = self.encoder(x) # 对向量进行编码 x = self.decoder(x) # 对向量进行解码 x = x.permute(1, 0, 2) # 将输出的向量转换为(batch_size, height*width, input_dim)的形式 x = self.linear(x) # 对输出的向量进行线性变换 x = x.squeeze(-1) # 去掉最后一维 return x ``` 2. End-to-End Object Detection with Adaptive Clustering Transformer(北大&港中文) 该论文提出了一种新的End-to-End目标检测算法,称为Adaptive Clustering Transformer(ACT)。ACT通过将Transformer模型应用于目标检测任务中,实现了对图像中目标的检测和定位。具体来说,ACT将输入图像分成多个子区域,并将每个子区域表示为一个向量。然后,ACT使用Transformer模型对这些向量进行编码和解码,并通过聚类算法对编码后的向量进行聚类,以实现对目标的检测和定位。相比于传统的目标检测算法,ACT具有更好的性能和更高的效率。 以下是ACT的代码实现: ```python import torch import torch.nn as nn import torch.nn.functional as F class ACT(nn.Module): def __init__(self, input_dim, hidden_dim, num_heads, num_layers, num_clusters): super(ACT, self).__init__() self.input_dim = input_dim self.hidden_dim = hidden_dim self.num_heads = num_heads self.num_layers = num_layers self.num_clusters = num_clusters self.encoder_layer = nn.TransformerEncoderLayer(d_model=input_dim, nhead=num_heads, dim_feedforward=hidden_dim) self.encoder = nn.TransformerEncoder(encoder_layer=self.encoder_layer, num_layers=num_layers) self.decoder_layer = nn.TransformerDecoderLayer(d_model=input_dim, nhead=num_heads, dim_feedforward=hidden_dim) self.decoder = nn.TransformerDecoder(decoder_layer=self.decoder_layer, num_layers=num_layers) self.linear = nn.Linear(input_dim, num_clusters) def forward(self, x): x = x.permute(0, 3, 1, 2) # 将输入的图像转换为(batch_size, input_dim, height, width)的形式 x = x.reshape(x.shape[0], x.shape[1], -1) # 将图像分成多个子区域,并将每个子区域表示为一个向量 x = self.encoder(x) # 对向量进行编码 x = self.decoder(x) # 对向量进行解码 x = x.permute(1, 0, 2) # 将输出的向量转换为(batch_size, height*width, input_dim)的形式 x = self.linear(x) # 对输出的向量进行线性变换 x = F.softmax(x, dim=-1) # 对输出的向量进行softmax操作 x = x.reshape(x.shape[0], -1, self.num_clusters) # 将输出的向量分成多个子区域,并将每个子区域表示为一个概率分布 x = x.mean(dim=1) # 对每个子区域的概率分布进行平均 return x ```

“相关推荐”对你有帮助么?

  • 非常没帮助
  • 没帮助
  • 一般
  • 有帮助
  • 非常有帮助
提交
评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值