YOLOv8/YOLOv7/YOLOv5/YOLOv4/Faster-rcnn系列算法改进【NO.71】注意力机制Expectation-Maximization Attention(EMA模块)

前言
作为当前先进的深度学习目标检测算法YOLOv8,已经集合了大量的trick,但是还是有提高和改进的空间,针对具体应用场景下的检测难点,可以不同的改进方法。此后的系列文章,将重点对YOLOv8的如何改进进行详细的介绍,目的是为了给那些搞科研的同学需要创新点或者搞工程项目的朋友需要达到更好的效果提供自己的微薄帮助和参考。由于出到YOLOv8,YOLOv7、YOLOv5算法2020年至今已经涌现出大量改进论文,这个不论对于搞科研的同学或者已经工作的朋友来说,研究的价值和新颖度都不太够了,为与时俱进,以后改进算法以YOLOv7为基础,此前YOLOv5改进方法在YOLOv7同样适用,所以继续YOLOv5系列改进的序号。另外改进方法在YOLOv5等其他目标检测算法同样可以适用进行改进。希望能够对大家有帮助。

一、解决问题

这篇文章提出的方法主要用并行子网络代替一层层叠加。这有助于有效减少深度同时保持高性能。尝试用提出的方法改进目标检测算法中,提升目标检测效果。

二、基本原理

原文链接:1907.13426.pdf (arxiv.org)

代码链接:GitHub - XiaLiPKU/EMANet: The code for Expectation-Maximization Attention Networks for Semantic Segmentation (ICCV'2019 Oral)

 原文摘要:自注意机制已被广泛应用于各种任务。它旨在通过所有位置的特征的加权求和来计算每个位置的表示。因此,它可以捕获计算机视觉任务的长程关系。然而,它的计算成本很高,因为注意力图是针对所有其他位置计算的。在本文中,我们将注意机制制定为期望最大化方式,并迭代估计一组更紧凑的基础,其中注意力图是计算的。通过这些基础的加权求和,得到的表示是低秩的,并消除了输入中的噪声信息。所提出的期望最大化注意(EMA)模块对输入的方差具有鲁棒性,同时在内存和计算方面也很友好。此外,我们建立了基础维护和归一化方法来稳定其训练过程。我们在流行的语义分割基准数据集上进行了广泛的实验,包括PASCAL VOC、PASCAL Context和COCO Stuff,并在其中取得了新的记录。

三、​添加方法

原论文提出的部分参考源码如下所示:

import torch
from torch import nn

class EMA(nn.Module):
    def __init__(self, channels, factor=8):
        super(EMA, self).__init__()
        self.groups = factor
        assert channels // self.groups > 0
        self.softmax = nn.Softmax(-1)
        self.agp = nn.AdaptiveAvgPool2d((1, 1))
        self.pool_h = nn.AdaptiveAvgPool2d((None, 1))
        self.pool_w = nn.AdaptiveAvgPool2d((1, None))
        self.gn = nn.GroupNorm(channels // self.groups, channels // self.groups)
        self.conv1x1 = nn.Conv2d(channels // self.groups, channels // self.groups, kernel_size=1, stride=1, padding=0)
        self.conv3x3 = nn.Conv2d(channels // self.groups, channels // self.groups, kernel_size=3, stride=1, padding=1)

    def forward(self, x):
        b, c, h, w = x.size()
        group_x = x.reshape(b * self.groups, -1, h, w)  # b*g,c//g,h,w
        x_h = self.pool_h(group_x)
        x_w = self.pool_w(group_x).permute(0, 1, 3, 2)
        hw = self.conv1x1(torch.cat([x_h, x_w], dim=2))
        x_h, x_w = torch.split(hw, [h, w], dim=2)
        x1 = self.gn(group_x * x_h.sigmoid() * x_w.permute(0, 1, 3, 2).sigmoid())
        x2 = self.conv3x3(group_x)
        x11 = self.softmax(self.agp(x1).reshape(b * self.groups, -1, 1).permute(0, 2, 1))
        x12 = x2.reshape(b * self.groups, c // self.groups, -1)  # b*g, c//g, hw
        x21 = self.softmax(self.agp(x2).reshape(b * self.groups, -1, 1).permute(0, 2, 1))
        x22 = x1.reshape(b * self.groups, c // self.groups, -1)  # b*g, c//g, hw
        weights = (torch.matmul(x11, x12) + torch.matmul(x21, x22)).reshape(b * self.groups, 1, h, w)
        return (group_x * weights.sigmoid()).reshape(b, c, h, w)

改进后运行的网络层数以及参数如下所示,博主是在NWPU VHR-10遥感数据集进行训练测试,实验是有提升效果的。具体获取办法可私信获取改进后的YOLO项目百度链接。

四、总结

预告一下:下一篇内容将继续分享深度学习算法相关改进方法。有兴趣的朋友可以关注一下我,有问题可以留言或者私聊我哦

PS:该方法不仅仅是适用改进YOLOv5,也可以改进其他的YOLO网络以及目标检测网络,比如YOLOv7、v6、v4、v3,Faster rcnn ,ssd等。

最后,有需要的请关注私信我吧。关注免费领取深度学习算法学习资料!

YOLO系列算法改进方法 | 目录一览表

猜你喜欢

转载自blog.csdn.net/m0_70388905/article/details/131361576