Construindo o modelo Resnet-34 usando Pytorch - Um Guia para Iniciantes

Nó Fonte: 1075632

Este artigo foi publicado como parte do Blogathon de Ciência de Dados

Introdução

Aprendizado profundo evoluiu muito nos últimos anos e todos estamos entusiasmados em construir redes de arquitetura mais profundas para obter mais precisão para nossos modelos. Essas técnicas são amplamente testadas para trabalhos relacionados a imagens, como classificação, agrupamento ou síntese. Ir fundo pode parecer legal, mas não vai ajudar, pois as redes neurais enfrentam um problema chamado degradação.

A precisão é afetada em grande medida aqui. Isso também leva a um problema chamado descida de gradiente de desaparecimento. Isso não nos permitirá atualizar adequadamente os pesos durante a etapa de retropropagação. Durante a etapa de retropropagação, usamos a regra da cadeia, os derivados de cada camada conforme descemos na rede são multiplicados.

Se usarmos camadas mais profundas e tivermos camadas ocultas como sigmóide, os derivados serão reduzidos a menos de 0.25 em cada camada. Então, quando muitas derivadas de camadas são multiplicadas, o gradiente diminui exponencialmente e obtemos um valor muito pequeno que é inútil para o cálculo do gradiente. Isso levou à criação do Resnet pela Microsoft Research, que usou conexões ignoradas para evitar degradação. Neste artigo, discutiremos uma implementação da arquitetura ResNet de 34 camadas usando a estrutura Pytorch em Python.

problema de gradiente de desaparecimento Resnet-34
1 imagem

Conforme discutido acima, este diagrama nos mostra o problema do gradiente de desaparecimento. As derivadas das funções sigmóides são reduzidas abaixo de 0.25 e isso perde muitas informações ao atualizar os gradientes.

O problema com redes de aviões

problema com redes simples
2 imagem

Conforme mostrado na figura, vemos as redes planas, que possuem camadas mais profundas. À esquerda, temos o erro de trem e o erro de teste à direita. Estaríamos pensando que isso poderia ser um processo de overfitting, mas aqui a% de erro da rede de 56 camadas é muito pior tanto no treinamento quanto nos dados de teste, o que não acontece quando o modelo está overfitting. Isso é chamado de degradação.

Arquitetura do Resnet-34

Arquitetura do Resnet-34
3 imagem

Inicialmente, temos uma camada convolucional que possui 64 filtros com um tamanho de kernel de 7 × 7 este é o primeira convolução, em seguida, seguido por uma camada de pooling máximo. Temos a passada especificada como 2 em ambos os casos. A seguir, em conv2_x temos a camada de agrupamento e as seguintes camadas de convolução. Essas camadas são normalmente agrupadas em pares devido à forma como os resíduos estão conectados (as setas mostram que estão pulando a cada duas camadas).

Aqui, temos as 2 camadas das quais têm um kernel_sizeof 3 × 3, num_filters de 64, e todas essas são repetidas x3, o que corresponde às camadas entre o pool, / 2 e o filtro 128 uns, 6 camadas no total (uma par vezes 3). Essas 2 camadas são kernel_size de 3 × 3, num_filters é 128 e eles também são repetidos, mas dessa vez 4. Isso continua até a função avg_pooling e a função softmax. Cada vez que o número de filtros é duplicado, podemos ver que a primeira camada especifica num_filters / 2.

Código para definir Resnet-34 em Pytorch:

classe ResNet34 (nn.Module): def __init __ (self): super (ResNet34, self) .__ init __ () self.block1 = nn.Sequential (nn.Conv2d (1,64, kernel_size = 2, stride = 2, padding = 3, bias = False), nn.BatchNorm2d (64), nn.ReLU (True)) self.block2 = nn.Sequential (nn.MaxPool2d (1,1), ResidualBlock (64,64), ResidualBlock (64,64,2 , 3)) self.block64,128 = nn.Sequential (ResidualBlock (128,128,2), ResidualBlock (4)) self.block128,256 = nn.Sequential (ResidualBlock (256,256,2), ResidualBlock (5)) self.block256,512 = nn. Sequencial (ResidualBlock (512,512,2), ResidualBlock (2)) self.avgpool = nn.AvgPool2d (1) # vowel_diacritic self.fc512,11 = nn.Linear (2) # grapheme_root self.fc512,168 = nn.Linear (3) # consonant_diacritic self.fc512,7 = nn.Linear (1) def forward (self, x): x = self.block2 (x) x = self.block3 (x) x = self.block4 (x) x = self. bloco5 (x) x = self.block0 (x) x = self.avgpool (x) x = x.view (x.size (1), - 1) x1 = self.fc2 (x) x2 = self.fc3 ( x) x3 = self.fc1 (x) retornar x2, x3, xXNUMX

Este código nos dá a implementação completa de um módulo para Resnet-34. Agora, vamos aprofundar no entendimento de como cada linha funciona. Para isso, vamos encurtar a arquitetura que vimos anteriormente. Consulte os 34 diagramas em camadas abaixo.

saída de código
4 imagem

Podemos ver que precisamos implementar qualquer arquitetura Resnet em 5 blocos. O primeiro bloco tem 64 filtros com um passo de 2. seguido por pooling máximo com um passo 2. A arquitetura usa preenchimento de 3. Como há uma chance de mudança de covariável interna, devemos estabilizar a rede por normalização em lote. Usamos a ativação ReLU no final. O primeiro bloco é o mesmo para qualquer arquitetura e os blocos restantes são alterados para camadas diferentes e são repetidos em um padrão específico. O primeiro bloco pode ser implementado como:

nn.Conv2d(1,64,kernel_size=2,stride=2,padding=3,bias=False),
nn.BatchNorm2d(64),
nn.ReLU(True)

Neste ponto, temos uma conexão de salto. Qual é a ideia principal das redes residuais. O diagrama de arquitetura que vimos anteriormente tinha conexões ignoradas mostradas com setas pontilhadas e escuras. A linha pontilhada é o que está acontecendo aqui, conforme estamos entrando em um canal com mais tamanho do que o anterior. O segundo bloco tem a implementação de um pool máximo inicial de 1 * 1 com um tamanho de kernel de 3 * 3 e dois blocos residuais conforme mostrado no código abaixo. Esses dois recebem 64 como canais de entrada e saída e são repetidos 3 vezes, conforme mostrado na arquitetura. No final, o último é conectado ao próximo bloco com uma passada de 2.

nn.MaxPool2d (1,1), ResidualBlock (64,64), ResidualBlock (64,64,2)

O conteúdo do último bloco foi repetido 3 vezes e indicamos que com a seta escura no diagrama da arquitetura o tamanho do canal de entrada e saída permanece o mesmo. O '/ 2' mostrado no diagrama de arquitetura nos informa sobre a passada usada.

O terceiro bloco tem um tamanho de kernel de 3 * 3 com um canal de entrada vindo do último bloco de 64 e dando um canal de saída de 128. Então, pegamos o mesmo 128 como canal de entrada e 128 como canal de saída. Repetimos isso 4 vezes, conforme mostrado no diagrama de arquitetura anterior.

ResidualBlock (64,128), ResidualBlock (128,128,2)

Da mesma forma, construímos nossos 4º e 5º blocos que têm 256 e 512 como tamanhos de kernel.

ResidualBlock (128,256), ResidualBlock (256,256,2)
ResidualBlock (256,512), ResidualBlock (512,512,2)

As funções lineares ajudam a conectar isso finalmente com a missão final que pode incluir etapas como classificar os conjuntos de dados cifar 10, etc. e a ideia é nivelar as camadas e dar um valor probabilístico para encontrar o máximo. E a função de avanço que definimos para conectar cada um dos blocos. Para a implementação completa do python, incluindo treinamento, você pode consultar este site do Network Development Group. Também podemos usar a técnica de aprendizagem por transferência de Pytorch e, para esse código, você pode consultar este GitHub repo.

Conclusão:

Referência:

  1. https://www.kaggle.com/khoongweihao/resnet-34-pytorch-starter-kit
  2. https://datascience.stackexchange.com/questions/33022/how-to-interpert-resnet50-layer-types

Sobre mim: Sou um Aluno Pesquisador interessado na área de Aprendizado Profundo e Processamento de Linguagem Natural e atualmente cursando pós-graduação em Inteligência Artificial.

Image Source

  1. Imagem 1,2: https://towardsdatascience.com/the-vanishing-gradient-problem-69bf08b15484
  2. Imagem 3,4: https://datascience.stackexchange.com/questions/33022/how-to-interpert-resnet50-layer-types
  3. Imagem de visualização: https://www.zdnet.com/pictures/10-cool-robots-at-this-years-robobusiness-conference/2/

Sinta-se à vontade para se conectar comigo em:

  1. Linkedin: https://www.linkedin.com/in/siddharth-m-426a9614a/
  2. Github: https://github.com/Siddharth1698

As mídias mostradas neste artigo no ResNet-34 não são propriedade da Analytics Vidhya e são usadas a critério do autor.

Fonte: https://www.analyticsvidhya.com/blog/2021/09/building-resnet-34-model-using-pytorch-a-guide-for-beginners/

Carimbo de hora:

Mais de Análise Vidhya