La position actuelle:Accueil du site>[notes de thèse] epsanet: An Efficiency Pyramid Squeeze attachment Block on Voluntary Neural Network

[notes de thèse] epsanet: An Efficiency Pyramid Squeeze attachment Block on Voluntary Neural Network

2022-05-15 07:05:57M0 61899108

Documents

Titre de la thèse:EPSANet: An Efficient Pyramid Squeeze Attention Block on Convolutional Neural Network

Inclus:CVPR2021

Adresse de la thèse:https://arxiv.org/abs/2105.14447

Adresse du projet:GitHub - murufeng/EPSANet

Questions&Résolution

L'utilisation de l'attention des canaux et de l'attention spatiale peut améliorer les performances.Par exemple:,SEModule,Améliorer les performances à moindre coût,Mais seules les informations sur les canaux sont prises en considération,Ignorer les informations spatiales;BAMEtCBAMCombiner l'attention spatiale et l'attention canalisée pour enrichir la carte de l'attention.Mais il reste deux questions:

  • Comment saisir et utiliser efficacement l'information spatiale des cartes caractéristiques à différentes échelles pour enrichir l'espace caractéristique;
  • L'attention du canal ou de l'espace ne peut saisir efficacement que l'information locale , Difficile à construire long-range Dépendance du canal pour .

Bien que les méthodes existantes puissent résoudre les problèmes susmentionnés , Mais cela augmente la complexité du modèle et les frais généraux de calcul . Cet article propose un module d'attention peu coûteux et efficace —— La pyramide comprime l'attention (Pyramid Squeeze Attention,PSA), Pour apprendre le poids de l'attention avec une complexité de modèle plus faible , Et intégrer efficacement l'attention locale et l'attention globale pour créer long-range Dépendance à long terme à l'égard de l'accès .PSA Le module peut traiter l'information spatiale de la carte des caractéristiques d'entrée à plusieurs échelles et établir efficacement la dépendance à long terme de l'attention des canaux à plusieurs échelles. .Et puis,Oui.PSA Remplacement du moduleResNetRéseauBottleneckDans3x3Convolution,Le reste reste reste reste inchangé,J'ai un nouveauEPSA(efficient pyramid split attention)Module.Basé surEPSA block La thèse construit un nouveau réseau de base EPSANet. Il peut fournir une forte capacité de représentation des caractéristiques à plusieurs échelles .EPSANet Dans la reconnaissance d'image Top-1 Acc Beaucoup mieux que l'état de la technique , Et plus efficace dans le calcul des paramètres .

Principales contributions

  • Proposer une nouvelleEfficient Pyramid Squeeze Attention(EPSA)Bloc, Extraction efficace d'informations spatiales à plusieurs échelles plus fines , Et le développement long-range Dépendances des canaux distants ;Flexible et extensible,Pour une variété d'architectures de réseau.
  • PrésentationEPSANetRéseau de base, Vous pouvez apprendre une représentation plus riche des caractéristiques à plusieurs échelles et calibrer de façon adaptative le poids d'attention du Canal à travers les dimensions .
  • EPSANetInImageNetEtCOCOClassification des images sur les ensembles de données、Détection des cibles、 La segmentation des instances donne de bons résultats .

Méthodes

Le mécanisme d'attention aux canaux permet au réseau de peser sélectivement l'importance de chaque canal , Pour générer plus d'informations .

SEModule

SE Le bloc se compose de deux parties :SqueezeCompression etExcitationMotivation, Utilisé respectivement pour encoder l'information globale et recalibrer les relations de canaux adaptatifs . Les données des canaux sont poolées à l'aide de la moyenne globale GAPPour générer, Intégrer des informations spatiales globales dans la description du canal . La formule de mise en commun de la moyenne globale est :

  Ensuite, l'information linéaire entre les canaux est combinée avec deux couches de connexion complètes , Aide à l'échange d'informations de haute et de basse dimension sur les canaux .c-th Formule de calcul du poids du canal :

 Et Représente deux couches de connexion complètes chacune , Réduction précédente , Cette dernière dimension restaure .

PSAModule

Le but principal de cet article est d'établir un mécanisme d'attention de canal plus efficace .À cette fin,, Une nouvelle pyramide est proposée pour réduire l'attention (PSA)Module.PSA Le module est réalisé principalement en quatre étapes :

  • Tout d'abord,,UtilisationSPC Module pour couper les canaux , Ensuite, l'extraction de caractéristiques à plusieurs échelles est effectuée pour l'information spatiale sur chaque carte de caractéristiques de Canal. ;
  • Deuxièmement,UtilisationSEWeight Module d'extraction de l'attention du canal pour les cartes de caractéristiques à différentes échelles , Obtenir le vecteur d'attention du Canal à chaque échelle ;
  • Troisièmement,UtilisationSoftmax Recalibrage des caractéristiques du vecteur d'attention multicanal , Obtenir le poids de l'attention après une nouvelle interaction Multi - canaux .
  • Quatrièmement, Multiplier les poids recalibrés et les cartes de caractéristiques correspondantes par éléments , Sortie d'un graphique de caractéristiques pondéré par l'attention avec des informations de caractéristiques à plusieurs échelles . Cette carte caractéristique a une plus grande capacité de représentation de l'information à plusieurs échelles .

SPCModule

PSA Le module le plus important pour réaliser l'extraction de caractéristiques à plusieurs échelles est SPC. 

 Parmi eux,

  Ensuite, les cartes de caractéristiques à plusieurs échelles sont combinées pour obtenir des cartes de caractéristiques. F.

EPSANet

EPSA block La structure est illustrée à l'extrême droite ,PrincipalementResNetMoyennebottleneckEn partie3x3Convolution remplacée parPSA module. 

Basé surEPSA block, Le document propose une nouvelle architecture de réseau de base :EPSANet,Et selonPSA module Taille de la convolution du Groupe dans , La structure spécifique du réseau est configurée comme suit :

L'expérience

Détails

Résultats

Il suffit de regarder le graphique ,Réseau、Le tronc、Paramètres,Comparaison des performances, C'est plus clair .

ImageNet Classification des images

 COCO2017 Détection des cibles

 COCO2017 Segmentation des instances

Code principal

 SE_weight_module.py

import torch.nn as nn

class SEWeightModule(nn.Module):

    def __init__(self, channels, reduction=16):
        super(SEWeightModule, self).__init__()
        self.avg_pool = nn.AdaptiveAvgPool2d(1)
        self.fc1 = nn.Conv2d(channels, channels//reduction, kernel_size=1, padding=0)
        self.relu = nn.ReLU(inplace=True)
        self.fc2 = nn.Conv2d(channels//reduction, channels, kernel_size=1, padding=0)
        self.sigmoid = nn.Sigmoid()

    def forward(self, x):
        out = self.avg_pool(x)
        out = self.fc1(out)
        out = self.relu(out)
        out = self.fc2(out)
        weight = self.sigmoid(out)

        return weight

epsanet.py

import torch
import torch.nn as nn
import math
from .SE_weight_module import SEWeightModule

def conv(in_planes, out_planes, kernel_size=3, stride=1, padding=1, dilation=1, groups=1):
    """standard convolution with padding"""
    return nn.Conv2d(in_planes, out_planes, kernel_size=kernel_size, stride=stride,
                     padding=padding, dilation=dilation, groups=groups, bias=False)

def conv1x1(in_planes, out_planes, stride=1):
    """1x1 convolution"""
    return nn.Conv2d(in_planes, out_planes, kernel_size=1, stride=stride, bias=False)

class PSAModule(nn.Module):

    def __init__(self, inplans, planes, conv_kernels=[3, 5, 7, 9], stride=1, conv_groups=[1, 4, 8, 16]):
        super(PSAModule, self).__init__()
        self.conv_1 = conv(inplans, planes//4, kernel_size=conv_kernels[0], padding=conv_kernels[0]//2,
                            stride=stride, groups=conv_groups[0])
        self.conv_2 = conv(inplans, planes//4, kernel_size=conv_kernels[1], padding=conv_kernels[1]//2,
                            stride=stride, groups=conv_groups[1])
        self.conv_3 = conv(inplans, planes//4, kernel_size=conv_kernels[2], padding=conv_kernels[2]//2,
                            stride=stride, groups=conv_groups[2])
        self.conv_4 = conv(inplans, planes//4, kernel_size=conv_kernels[3], padding=conv_kernels[3]//2,
                            stride=stride, groups=conv_groups[3])
        self.se = SEWeightModule(planes // 4)
        self.split_channel = planes // 4
        self.softmax = nn.Softmax(dim=1)

    def forward(self, x):
        batch_size = x.shape[0]
        x1 = self.conv_1(x)
        x2 = self.conv_2(x)
        x3 = self.conv_3(x)
        x4 = self.conv_4(x)

        feats = torch.cat((x1, x2, x3, x4), dim=1)
        feats = feats.view(batch_size, 4, self.split_channel, feats.shape[2], feats.shape[3])

        x1_se = self.se(x1)
        x2_se = self.se(x2)
        x3_se = self.se(x3)
        x4_se = self.se(x4)

        x_se = torch.cat((x1_se, x2_se, x3_se, x4_se), dim=1)
        attention_vectors = x_se.view(batch_size, 4, self.split_channel, 1, 1)
        attention_vectors = self.softmax(attention_vectors)
        feats_weight = feats * attention_vectors
        for i in range(4):
            x_se_weight_fp = feats_weight[:, i, :, :]
            if i == 0:
                out = x_se_weight_fp
            else:
                out = torch.cat((x_se_weight_fp, out), 1)

        return out


class EPSABlock(nn.Module):
    expansion = 4

    def __init__(self, inplanes, planes, stride=1, downsample=None, norm_layer=None, conv_kernels=[3, 5, 7, 9],
                 conv_groups=[1, 4, 8, 16]):
        super(EPSABlock, self).__init__()
        if norm_layer is None:
            norm_layer = nn.BatchNorm2d
        # Both self.conv2 and self.downsample layers downsample the input when stride != 1
        self.conv1 = conv1x1(inplanes, planes)
        self.bn1 = norm_layer(planes)
        self.conv2 = PSAModule(planes, planes, stride=stride, conv_kernels=conv_kernels, conv_groups=conv_groups)
        self.bn2 = norm_layer(planes)
        self.conv3 = conv1x1(planes, planes * self.expansion)
        self.bn3 = norm_layer(planes * self.expansion)
        self.relu = nn.ReLU(inplace=True)
        self.downsample = downsample
        self.stride = stride

    def forward(self, x):
        identity = x

        out = self.conv1(x)
        out = self.bn1(out)
        out = self.relu(out)

        out = self.conv2(out)
        out = self.bn2(out)
        out = self.relu(out)

        out = self.conv3(out)
        out = self.bn3(out)

        if self.downsample is not None:
            identity = self.downsample(x)

        out += identity
        out = self.relu(out)
        return out


class EPSANet(nn.Module):
    def __init__(self,block, layers, num_classes=1000):
        super(EPSANet, self).__init__()
        self.inplanes = 64
        self.conv1 = nn.Conv2d(3, 64, kernel_size=7, stride=2, padding=3, bias=False)
        self.bn1 = nn.BatchNorm2d(64)
        self.relu = nn.ReLU(inplace=True)
        self.maxpool = nn.MaxPool2d(kernel_size=3, stride=2, padding=1)
        self.layer1 = self._make_layers(block, 64, layers[0], stride=1)
        self.layer2 = self._make_layers(block, 128, layers[1], stride=2)
        self.layer3 = self._make_layers(block, 256, layers[2], stride=2)
        self.layer4 = self._make_layers(block, 512, layers[3], stride=2)
        self.avgpool = nn.AdaptiveAvgPool2d((1, 1))
        self.fc = nn.Linear(512 * block.expansion, num_classes)

        for m in self.modules():
            if isinstance(m, nn.Conv2d):
                n = m.kernel_size[0] * m.kernel_size[1] * m.out_channels
                m.weight.data.normal_(0, math.sqrt(2. / n))
            elif isinstance(m, nn.BatchNorm2d):
                m.weight.data.fill_(1)
                m.bias.data.zero_()

    def _make_layers(self, block, planes, num_blocks, stride=1):
        downsample = None
        if stride != 1 or self.inplanes != planes * block.expansion:
            downsample = nn.Sequential(
                nn.Conv2d(self.inplanes, planes * block.expansion,
                          kernel_size=1, stride=stride, bias=False),
                nn.BatchNorm2d(planes * block.expansion),
            )

        layers = []
        layers.append(block(self.inplanes, planes, stride, downsample))
        self.inplanes = planes * block.expansion
        for i in range(1, num_blocks):
            layers.append(block(self.inplanes, planes))

        return nn.Sequential(*layers)

    def forward(self, x):
        x = self.conv1(x)
        x = self.bn1(x)
        x = self.relu(x)
        x = self.maxpool(x)

        x = self.layer1(x)
        x = self.layer2(x)
        x = self.layer3(x)
        x = self.layer4(x)

        x = self.avgpool(x)
        x = x.view(x.size(0), -1)
        x = self.fc(x)

        return x


def epsanet50():
    model = EPSANet(EPSABlock, [3, 4, 6, 3], num_classes=1000)
    return model

def epsanet101():
    model = EPSANet(EPSABlock, [3, 4, 23, 3], num_classes=1000)
    return model

Blog de référence

EPSANet: Un mécanisme d'attention multicanal efficace , Le module de segmentation pyramidale de l'attention est principalement proposé ,Plug and play,L'effet est remarquable.,Open Source! - Oui.

C'est vraiment trop détaillé !!!

Mentions de copyright
Auteur de cet article [M0 61899108],Réimpression s’il vous plaît apporter le lien vers l’original, merci
https://fra.chowdera.com/2022/135/202205142322538951.html

Recommandé au hasard