Výukový program PyTorch: Regrese, příklad klasifikace obrázků
Shrnutí výukového programu Pytorch
V tomto tutoriálu pytorch se naučíte všechny koncepty od začátku. Tento tutoriál pokrývá základní až pokročilá témata, jako je definice pytorch, výhody a nevýhody pytorch, srovnání, instalace, rámec pytorch, regrese a klasifikace obrázků. Tento pytorch tutoriál je zcela zdarma.
Co je PyTorch?
PyTorch je open-source knihovna strojového učení založená na Torch pro zpracování přirozeného jazyka Python. Je podobný NumPy, ale s výkonnou podporou GPU. Nabízí dynamické výpočetní grafy, které můžete upravovat na cestách pomocí autogradu. PyTorch je také rychlejší než některé jiné frameworky. Byl vyvinut výzkumnou skupinou AI na Facebooku v roce 2016.
Výhody a nevýhody PyTorch
Níže jsou uvedeny výhody a nevýhody PyTorch:
Výhody PyTorch
- Jednoduchá knihovna
Kód PyTorch je jednoduchý. Je snadno srozumitelná a knihovnu používáte okamžitě. Podívejte se například na fragment kódu níže:
class Net(torch.nn.Module): def __init__(self): super(Net, self).__init__() self.layer = torch.nn.Linear(1, 1) def forward(self, x): x = self.layer(x) return x
Jak bylo zmíněno výše, model sítě můžete definovat snadno a kódu rychle porozumíte bez velkého školení.
- Dynamický výpočetní graf
Zdroj obrázku: Exploring Deep Learning with PyTorch
Pytorch nabízí Dynamic Computational Graph (DAG). Výpočtové grafy představují způsob, jak vyjádřit matematické výrazy v modelech grafů nebo teoriích, jako jsou uzly a hrany. Uzel provede matematickou operaci a hrana je tenzor, který bude přiváděn do uzlů a nese výstup uzlu v Tensoru.
DAG je graf, který má libovolný tvar a je schopen provádět operace mezi různými vstupními grafy. Při každé iteraci se vytvoří nový graf. Je tedy možné mít stejnou strukturu grafu nebo vytvořit nový graf s jinou operací, nebo to můžeme nazvat dynamickým grafem.
- Lepší výkon
Komunity a výzkumní pracovníci, porovnávat a porovnávat rámce, abyste zjistili, který z nich je rychlejší. Úložiště GitHub Srovnání rámců hlubokého učení a GPU uvedl, že PyTorch je rychlejší než ostatní frameworky, pokud jde o obrázky zpracované za sekundu.
Jak můžete vidět níže, srovnávací grafy s vgg16 a resnet152
- Domácí Python
PyTorch je více založen na pythonu. Pokud například chcete trénovat model, můžete použít nativní řídicí tok, jako je smyčkování a rekurze, aniž byste museli přidávat další speciální proměnné nebo relace, abyste je mohli spouštět. To je velmi užitečné pro tréninkový proces.
Pytorch také implementuje imperativní programování a je rozhodně flexibilnější. Je tedy možné vytisknout hodnotu tenzoru uprostřed procesu výpočtu.
Nevýhoda PyTorch
PyTorch vyžaduje pro vizualizaci aplikace třetích stran. Pro produkci také potřebuje server API.
Dále v tomto tutoriálu PyTorch se dozvíme o rozdílu mezi PyTorchem a TensorFlow.
PyTorch vs. Tensorflow
Parametr | PyTorch | tenzorový tok |
---|---|---|
Definice modelu | Model je definován v podtřídě a nabízí snadno použitelný balíček | Model je definován mnoha a musíte rozumět syntaxi |
Podpora GPU | Ano | Ano |
Typ grafu | Dynamický | statický |
Tools | Žádný vizualizační nástroj | Můžete použít vizualizační nástroj Tensorboard |
Naše projekty | Komunita stále roste | Velké aktivní komunity |
Instalace PyTorch
Linux
Instalace v Linuxu je jednoduchá. Můžete se rozhodnout použít virtuální prostředí nebo jej nainstalovat přímo s přístupem root. Zadejte tento příkaz do terminálu
pip3 install --upgrade torch torchvision
AWS Sagemaker
Sagemaker je jednou z platforem Amazon Webová služba který nabízí výkonný stroj pro strojové učení s předinstalovanými konfiguracemi hlubokého učení pro datové vědce nebo vývojáře, aby mohli vytvářet, trénovat a nasazovat modely v jakémkoli měřítku.
Nejprve otevřete Amazon Sagemaker konzole a klikněte na Vytvořit instanci notebooku a vyplňte všechny podrobnosti o svém notebooku.
V dalším kroku klikněte na Otevřít pro spuštění instance notebooku.
Nakonec In Jupyter, Klikněte na Nový a vyberte conda_pytorch_p36 a jste připraveni používat instanci notebooku s nainstalovaným Pytorchem.
Dále v tomto tutoriálu PyTorch se seznámíme se základy rámce PyTorch.
Základy rámce PyTorch
Naučme se základní koncepty PyTorch, než se pustíme do hloubky. PyTorch používá Tensor pro každou proměnnou podobnou ndarray numpy, ale s podporou výpočtu GPU. Zde vysvětlíme model sítě, ztrátovou funkci, Backprop a Optimizer.
Model sítě
Síť lze vytvořit podtřídou torch.nn. Má 2 hlavní části,
- První částí je definovat parametry a vrstvy, které budete používat
- Druhá část je hlavní úkol zvaný dopředný proces, který bude mít vstup a předvídat výstup.
Import torch import torch.nn as nn import torch.nn.functional as F class Model(nn.Module): def __init__(self): super(Model, self).__init__() self.conv1 = nn.Conv2d(3, 20, 5) self.conv2 = nn.Conv2d(20, 40, 5) self.fc1 = nn.Linear(320, 10) def forward(self, x): x = F.relu(self.conv1(x)) x = F.relu(self.conv2(x)) x = x.view(-1, 320) x = F.relu(self.fc1(x)) return F.log_softmax(x) net = Model()
Jak můžete vidět výše, vytvoříte třídu nn.Module s názvem Model. Obsahuje 2 vrstvy Conv2d a lineární vrstvu. První vrstva conv2d má vstup 3 a výstupní tvar 20. Druhá vrstva bude mít vstup 20 a vytvoří výstupní tvar 40. Poslední vrstva je plně propojená vrstva ve tvaru 320 a vytvoří výstup 10.
Dopředný proces vezme vstup X a přivede jej do vrstvy conv1 a provede funkci ReLU,
Podobně bude také napájet vrstvu conv2. Poté se x přetvoří na (-1, 320) a přivede se do finální FC vrstvy. Před odesláním výstupu využijete funkci aktivace softmax.
Zpětný proces je automaticky definován pomocí autogradu, takže stačí definovat pouze dopředný proces.
Ztrátová funkce
Ztrátová funkce se používá k měření toho, jak dobře je predikční model schopen předpovědět očekávané výsledky. PyTorch již má mnoho standardních ztrátových funkcí v modulu torch.nn. Například můžete použít Cross-Entropy Loss k vyřešení problému klasifikace PyTorch s více třídami. Je snadné definovat ztrátovou funkci a vypočítat ztráty:
loss_fn = nn.CrossEntropyLoss() #training process loss = loss_fn(out, target)
S PyTorchem je snadné použít vlastní výpočet ztrátové funkce.
Backprop
Chcete-li provést zpětné šíření, jednoduše zavoláte los.backward(). Chyba bude vypočítána, ale nezapomeňte vymazat existující přechod pomocí zero_grad()
net.zero_grad() # to clear the existing gradient loss.backward() # to perform backpropragation
Optimalizátor
Torch.optim poskytuje běžné optimalizační algoritmy. Optimalizátor můžete definovat jednoduchým krokem:
optimizer = torch.optim.SGD(net.parameters(), lr = 0.01, momentum=0.9)
Musíte předat parametry modelu sítě a rychlost učení, aby se při každé iteraci parametry po procesu backprop aktualizovaly.
Jednoduchá regrese s PyTorchem
Pojďme se naučit jednoduchou regresi s příklady PyTorch:
Krok 1) Vytvoření našeho síťového modelu
Náš síťový model je jednoduchá lineární vrstva se vstupním a výstupním tvarem 1.
from __future__ import print_function import torch import torch.nn as nn import torch.nn.functional as F from torch.autograd import Variable class Net(nn.Module): def __init__(self): super(Net, self).__init__() self.layer = torch.nn.Linear(1, 1) def forward(self, x): x = self.layer(x) return x net = Net() print(net)
A síťový výstup by měl být takový
Net( (hidden): Linear(in_features=1, out_features=1, bias=True) )
Krok 2) Testovací data
Než začnete s tréninkovým procesem, musíte znát naše údaje. Vytvoříte náhodnou funkci pro testování našeho modelu. Y = x3 sin(x)+ 3x+0.8 rand (100)
# Visualize our data import matplotlib.pyplot as plt import numpy as np x = np.random.rand(100) y = np.sin(x) * np.power(x,3) + 3*x + np.random.rand(100)*0.8 plt.scatter(x, y) plt.show()
Zde je bodový graf naší funkce:
Než začnete s tréninkovým procesem, musíte převést numpy pole na proměnné, které podporuje Torch a autograd, jak je znázorněno v níže uvedeném příkladu regrese PyTorch.
# convert numpy array to tensor in shape of input size x = torch.from_numpy(x.reshape(-1,1)).float() y = torch.from_numpy(y.reshape(-1,1)).float() print(x, y)
Krok 3) Optimalizátor a ztráta
Dále byste měli definovat Optimizer a Loss Function pro náš tréninkový proces.
# Define Optimizer and Loss Function optimizer = torch.optim.SGD(net.parameters(), lr=0.2) loss_func = torch.nn.MSELoss()
Krok 4) Školení
Nyní začněme náš tréninkový proces. S epochou 250 budete opakovat naše data, abyste našli nejlepší hodnotu pro naše hyperparametry.
inputs = Variable(x) outputs = Variable(y) for i in range(250): prediction = net(inputs) loss = loss_func(prediction, outputs) optimizer.zero_grad() loss.backward() optimizer.step() if i % 10 == 0: # plot and show learning process plt.cla() plt.scatter(x.data.numpy(), y.data.numpy()) plt.plot(x.data.numpy(), prediction.data.numpy(), 'r-', lw=2) plt.text(0.5, 0, 'Loss=%.4f' % loss.data.numpy(), fontdict={'size': 10, 'color': 'red'}) plt.pause(0.1) plt.show()
Krok 5) Výsledek
Jak můžete vidět níže, úspěšně jste provedli regresi PyTorch pomocí neuronové sítě. Ve skutečnosti se při každé iteraci červená čára v grafu aktualizuje a změní svou polohu tak, aby odpovídala datům. Ale na tomto obrázku vám ukáže pouze konečný výsledek, jak je znázorněno v níže uvedeném příkladu PyTorch:
Příklad klasifikace obrázků pomocí PyTorch
Jedna z populárních metod, jak se naučit základy hluboké učení je s datovou sadou MNIST. Je to „Hello World“ v hlubokém učení. Dataset obsahuje ručně psaná čísla od 0 do 9 s celkem 60,000 10,000 trénovacími vzorky a 28 28 testovacími vzorky, které jsou již označeny velikostí XNUMX×XNUMX pixelů.
Krok 1) Předzpracování dat
V prvním kroku tohoto příkladu klasifikace PyTorch načtete datovou sadu pomocí modulu torchvision.
Než začnete s tréninkovým procesem, musíte datům porozumět. Torchvision načte datovou sadu a transformuje obrázky podle příslušných požadavků pro síť, jako je tvar a normalizace obrázků.
import torch import torchvision import numpy as np from torchvision import datasets, models, transforms # This is used to transform the images to Tensor and normalize it transform = transforms.Compose( [transforms.ToTensor(), transforms.Normalize((0.5, 0.5, 0.5), (0.5, 0.5, 0.5))]) training = torchvision.datasets.MNIST(root='./data', train=True, download=True, transform=transform) train_loader = torch.utils.data.DataLoader(training, batch_size=4, shuffle=True, num_workers=2) testing = torchvision.datasets.MNIST(root='./data', train=False, download=True, transform=transform) test_loader = torch.utils.data.DataLoader(testing, batch_size=4, shuffle=False, num_workers=2) classes = ('0', '1', '2', '3', '4', '5', '6', '7', '8', '9') import matplotlib.pyplot as plt import numpy as np #create an iterator for train_loader # get random training images data_iterator = iter(train_loader) images, labels = data_iterator.next() #plot 4 images to visualize the data rows = 2 columns = 2 fig=plt.figure() for i in range(4): fig.add_subplot(rows, columns, i+1) plt.title(classes[labels[i]]) img = images[i] / 2 + 0.5 # this is for unnormalize the image img = torchvision.transforms.ToPILImage()(img) plt.imshow(img) plt.show()
Funkce transformace převádí obrázky na tenzor a normalizuje hodnotu. Funkce torchvision.transforms.MNIST stáhne datovou sadu (pokud není dostupná) v adresáři, v případě potřeby nastaví datovou sadu pro trénování a provede proces transformace.
K vizualizaci datové sady použijte data_iterator k získání další dávky obrázků a štítků. K vykreslení těchto obrázků a jejich příslušného označení použijete matplot. Jak můžete vidět níže naše obrázky a jejich popisky.
Krok 2) Konfigurace síťového modelu
Nyní v tomto příkladu PyTorch vytvoříte jednoduchou neuronovou síť pro klasifikaci obrázků PyTorch.
Zde vám představujeme další způsob, jak vytvořit model sítě v PyTorch. Použijeme nn.Sequential k vytvoření sekvenčního modelu namísto vytvoření podtřídy nn.Module.
import torch.nn as nn # flatten the tensor into class Flatten(nn.Module): def forward(self, input): return input.view(input.size(0), -1) #sequential based model seq_model = nn.Sequential( nn.Conv2d(1, 10, kernel_size=5), nn.MaxPool2d(2), nn.ReLU(), nn.Dropout2d(), nn.Conv2d(10, 20, kernel_size=5), nn.MaxPool2d(2), nn.ReLU(), Flatten(), nn.Linear(320, 50), nn.ReLU(), nn.Linear(50, 10), nn.Softmax(), ) net = seq_model print(net)
Zde je výstup našeho síťového modelu
Sequential( (0): Conv2d(1, 10, kernel_size=(5, 5), stride=(1, 1)) (1): MaxPool2d(kernel_size=2, stride=2, padding=0, dilation=1, ceil_mode=False) (2): ReLU() (3): Dropout2d(p=0.5) (4): Conv2d(10, 20, kernel_size=(5, 5), stride=(1, 1)) (5): MaxPool2d(kernel_size=2, stride=2, padding=0, dilation=1, ceil_mode=False) (6): ReLU() (7): Flatten() (8): Linear(in_features=320, out_features=50, bias=True) (9): ReLU() (10): Linear(in_features=50, out_features=10, bias=True) (11): Softmax() )
Vysvětlení sítě
- Sekvence je taková, že první vrstva je vrstva Conv2D se vstupním tvarem 1 a výstupním tvarem 10 s velikostí jádra 5
- Dále máte vrstvu MaxPool2D
- Aktivační funkce ReLU
- vrstva Dropout pro snížení hodnot s nízkou pravděpodobností.
- Poté druhý Conv2d se vstupním tvarem 10 z poslední vrstvy a výstupním tvarem 20 s velikostí jádra 5
- Dále vrstva MaxPool2d
- Funkce aktivace ReLU.
- Poté tenzor zploštíte, než jej vložíte do lineární vrstvy
- Lineární vrstva bude mapovat náš výstup na druhé lineární vrstvě s funkcí aktivace softmax
Krok 3) Trénujte model
Před zahájením tréninkového procesu je nutné nastavit kritérium a funkci optimalizátoru.
Jako kritérium použijete CrossEntropyLoss. Pro Optimizer použijete SGD s rychlostí učení 0.001 a hybností 0.9, jak je ukázáno v níže uvedeném příkladu PyTorch.
import torch.optim as optim criterion = nn.CrossEntropyLoss() optimizer = optim.SGD(net.parameters(), lr=0.001, momentum=0.9)
Dopředný proces převezme vstupní tvar a předá jej první vrstvě conv2d. Poté bude přiváděn do maxpool2d a nakonec uveden do funkce aktivace ReLU. Ke stejnému procesu dojde ve druhé vrstvě conv2d. Poté bude vstup přetvořen na (-1,320 XNUMX) a přiveden do fc vrstvy, aby se předpověděl výstup.
Nyní zahájíte tréninkový proces. Projdete naši datovou sadu 2krát nebo s epochou 2 a vytisknete aktuální ztrátu při každé dávce 2000.
for epoch in range(2): #set the running loss at each epoch to zero running_loss = 0.0 # we will enumerate the train loader with starting index of 0 # for each iteration (i) and the data (tuple of input and labels) for i, data in enumerate(train_loader, 0): inputs, labels = data # clear the gradient optimizer.zero_grad() #feed the input and acquire the output from network outputs = net(inputs) #calculating the predicted and the expected loss loss = criterion(outputs, labels) #compute the gradient loss.backward() #update the parameters optimizer.step() # print statistics running_loss += loss.item() if i % 1000 == 0: print('[%d, %5d] loss: %.3f' % (epoch + 1, i + 1, running_loss / 1000)) running_loss = 0.0
V každé epoše získá čítač další n-tici vstupů a odpovídajících štítků. Než přivedeme vstup do našeho síťového modelu, musíme vymazat předchozí gradient. To je vyžadováno, protože po zpětném procesu (proces zpětného šíření) bude gradient namísto nahrazení akumulován. Poté spočítáme ztráty z predikovaného výkonu z očekávaného výkonu. Poté provedeme backpropagation pro výpočet gradientu a nakonec aktualizujeme parametry.
Zde je výstup z tréninkového procesu
[1, 1] loss: 0.002 [1, 1001] loss: 2.302 [1, 2001] loss: 2.295 [1, 3001] loss: 2.204 [1, 4001] loss: 1.930 [1, 5001] loss: 1.791 [1, 6001] loss: 1.756 [1, 7001] loss: 1.744 [1, 8001] loss: 1.696 [1, 9001] loss: 1.650 [1, 10001] loss: 1.640 [1, 11001] loss: 1.631 [1, 12001] loss: 1.631 [1, 13001] loss: 1.624 [1, 14001] loss: 1.616 [2, 1] loss: 0.001 [2, 1001] loss: 1.604 [2, 2001] loss: 1.607 [2, 3001] loss: 1.602 [2, 4001] loss: 1.596 [2, 5001] loss: 1.608 [2, 6001] loss: 1.589 [2, 7001] loss: 1.610 [2, 8001] loss: 1.596 [2, 9001] loss: 1.598 [2, 10001] loss: 1.603 [2, 11001] loss: 1.596 [2, 12001] loss: 1.587 [2, 13001] loss: 1.596 [2, 14001] loss: 1.603
Krok 4) Otestujte model
Poté, co natrénujete náš model, musíte jej otestovat nebo vyhodnotit s jinými sadami obrázků.
Pro test_loader použijeme iterátor a ten vygeneruje dávku obrázků a štítků, které budou předány trénovanému modelu. Předpokládaný výstup se zobrazí a porovná s očekávaným výstupem.
#make an iterator from test_loader #Get a batch of training images test_iterator = iter(test_loader) images, labels = test_iterator.next() results = net(images) _, predicted = torch.max(results, 1) print('Predicted: ', ' '.join('%5s' % classes[predicted[j]] for j in range(4))) fig2 = plt.figure() for i in range(4): fig2.add_subplot(rows, columns, i+1) plt.title('truth ' + classes[labels[i]] + ': predict ' + classes[predicted[i]]) img = images[i] / 2 + 0.5 # this is to unnormalize the image img = torchvision.transforms.ToPILImage()(img) plt.imshow(img) plt.show()
Shrnutí
- PyTorch je open-source založený na Torchu Strojové učení knihovna pro zpracování přirozeného jazyka použitím Python.
- Výhody PyTorch: 1) Jednoduchá knihovna, 2) Dynamický výpočetní graf, 3) Lepší výkon, 4) Nativní Python
- PyTorch používá Tensor pro každou proměnnou podobnou ndarray numpy, ale s podporou výpočtu GPU.
- Jednou z populárních metod, jak se naučit základy hlubokého učení, je datová sada MNIST.