Mizející a explodující gradienty

Intermediate Deep Learning with PyTorch

Michal Oleszak

Machine Learning Engineer

Mizející gradienty

  • Gradienty se při zpětném průchodu zmenšují
  • Dřívější vrstvy dostávají malé aktualizace parametrů
  • Model se neučí

Grafy zobrazující velikost gradientu v závislosti na indexu vrstvy: pro dřívější vrstvy jsou gradienty menší

Intermediate Deep Learning with PyTorch

Explodující gradienty

  • Gradienty se neustále zvětšují
  • Aktualizace parametrů jsou příliš velké
  • Trénování diverguje

Grafy zobrazující velikost gradientu v závislosti na indexu vrstvy: pro dřívější vrstvy jsou gradienty větší

Intermediate Deep Learning with PyTorch

Řešení nestabilních gradientů

  1. Správná inicializace vah
  2. Vhodné aktivační funkce
  3. Dávková normalizace

 

 

Tři kroky

Intermediate Deep Learning with PyTorch

Inicializace vah

layer = nn.Linear(8, 1)
print(layer.weight)
Parameter containing:
tensor([[-0.0195,  0.0992,  0.0391,  0.0212,
         -0.3386, -0.1892, -0.3170,  0.2148]])
Intermediate Deep Learning with PyTorch

Inicializace vah

Správná inicializace zajišťuje:

  • Rozptyl vstupů vrstvy = rozptyl výstupů vrstvy
  • Rozptyl gradientů je před i za vrstvou stejný

 

Záleží na aktivační funkci:

  • Pro ReLU a podobné funkce: inicializace He/Kaiming
Intermediate Deep Learning with PyTorch

Inicializace vah

import torch.nn.init as init

init.kaiming_uniform_(layer.weight)
print(layer.weight)
Parameter containing:
tensor([[-0.3063, -0.2410,  0.0588,  0.2664,
          0.0502, -0.0136,  0.2274,  0.0901]])
Intermediate Deep Learning with PyTorch

Inicializace He / Kaiming

init.kaiming_uniform_(self.fc1.weight)
init.kaiming_uniform_(self.fc2.weight)
init.kaiming_uniform_(
  self.fc3.weight,
  nonlinearity="sigmoid",
)
Intermediate Deep Learning with PyTorch

Inicializace He / Kaiming

import torch.nn as nn
import torch.nn.init as init

class Net(nn.Module):
    def __init__(self):
        super().__init__()
        self.fc1 = nn.Linear(9, 16)
        self.fc2 = nn.Linear(16, 8)
        self.fc3 = nn.Linear(8, 1)


init.kaiming_uniform_(self.fc1.weight) init.kaiming_uniform_(self.fc2.weight) init.kaiming_uniform_( self.fc3.weight, nonlinearity="sigmoid", )




    def forward(self, x):
        x = nn.functional.relu(self.fc1(x))
        x = nn.functional.relu(self.fc2(x))
        x = nn.functional.sigmoid(self.fc3(x))
        return x







Intermediate Deep Learning with PyTorch

Aktivační funkce

Graf znázorňující funkci ReLU. Pro hodnoty pod nulou je přímka vodorovná na nule; pro hodnoty nad nulou má kladný sklon.

  • Často používaná výchozí aktivační funkce
  • nn.functional.relu()
  • Nulová pro záporné vstupy – umírající neurony

Graf znázorňující funkci ELU. Podobá se funkci ReLU, ale s plynulým zakřiveným přechodem ze záporných hodnot do kladné oblasti.

  • nn.functional.elu()
  • Nenulové gradienty pro záporné hodnoty – pomáhá proti umírajícím neuronům
  • Průměrný výstup kolem nuly – pomáhá proti mizejícím gradientům
Intermediate Deep Learning with PyTorch

Dávková normalizace

Po každé vrstvě:

  1. Normalizace výstupů vrstvy:

    • Odečtení průměru
    • Dělení směrodatnou odchylkou
  2. Škálování a posun normalizovaných výstupů pomocí naučených parametrů

Model se naučí optimální distribuci vstupů pro každou vrstvu:

  • Rychlejší pokles ztrátové funkce
  • Pomáhá proti nestabilním gradientům
Intermediate Deep Learning with PyTorch

Dávková normalizace

class Net(nn.Module):
    def __init__(self):
        super().__init__()
        self.fc1 = nn.Linear(9, 16)
        self.bn1 = nn.BatchNorm1d(16)

        ...


def forward(self, x): x = self.fc1(x) x = self.bn1(x) x = nn.functional.elu(x) ...
Intermediate Deep Learning with PyTorch

Pojďme si procvičit!

Intermediate Deep Learning with PyTorch

Preparing Video For Download...