Κοινή χρήση μέσω


Πώς να εκπαιδεύσετε μοντέλα με το PyTorch στο Microsoft Fabric

Το PyTorch είναι ένα πλαίσιο εκμάθησης μηχανής που βασίζεται στη βιβλιοθήκη Torch. Χρησιμοποιείται συχνά για εφαρμογές όπως η οπτική επεξεργασία υπολογιστών και η επεξεργασία φυσικής γλώσσας. Σε αυτό το άρθρο, θα δούμε ένα παράδειγμα του τρόπου με τον οποίο εκπαιδεύετε και παρακολουθείτε τις επαναλήψεις του μοντέλου σας PyTorch.

Εγκατάσταση του PyTorch

Για να ξεκινήσετε με το PyTorch, πρέπει να βεβαιωθείτε ότι εγκαθίσταται μέσα στο σημειωματάριό σας. Μπορείτε να εγκαταστήσετε ή να αναβαθμίσετε την έκδοση του PyTorch στο περιβάλλον σας, χρησιμοποιώντας την ακόλουθη εντολή:

%pip install torch

Ρύθμιση του πειράματος εκμάθησης μηχανής

Στη συνέχεια, δημιουργείτε ένα πείραμα εκμάθησης μηχανής χρησιμοποιώντας το MLFLow API. Το API MLflow set_experiment() δημιουργεί ένα νέο πείραμα εκμάθησης μηχανής, εάν δεν υπάρχει ήδη.

import mlflow

mlflow.set_experiment("sample-pytorch")

Εκπαίδευση και αξιολόγηση ενός μοντέλου Pytorch

Μετά τη δημιουργία του πειράματος, ο παρακάτω κώδικας φορτώνει το σύνολο δεδομένων MNSIT, δημιουργεί τα σύνολα δεδομένων δοκιμής και εκπαίδευσης και δημιουργεί μια λειτουργία εκπαίδευσης.

import os
import torch
import torch.nn as nn
from torch.autograd import Variable
import torchvision.datasets as dset
import torchvision.transforms as transforms
import torch.nn.functional as F
import torch.optim as optim


## load mnist dataset
root = "/tmp/mnist"
if not os.path.exists(root):
    os.mkdir(root)

trans = transforms.Compose(
    [transforms.ToTensor(), transforms.Normalize((0.5,), (1.0,))]
)
# if not exist, download mnist dataset
train_set = dset.MNIST(root=root, train=True, transform=trans, download=True)
test_set = dset.MNIST(root=root, train=False, transform=trans, download=True)

batch_size = 100

train_loader = torch.utils.data.DataLoader(
    dataset=train_set, batch_size=batch_size, shuffle=True
)
test_loader = torch.utils.data.DataLoader(
    dataset=test_set, batch_size=batch_size, shuffle=False
) 

print("==>>> total trainning batch number: {}".format(len(train_loader)))
print("==>>> total testing batch number: {}".format(len(test_loader)))

## network

class LeNet(nn.Module):
    def __init__(self):
        super(LeNet, self).__init__()
        self.conv1 = nn.Conv2d(1, 20, 5, 1)
        self.conv2 = nn.Conv2d(20, 50, 5, 1)
        self.fc1 = nn.Linear(4 * 4 * 50, 500)
        self.fc2 = nn.Linear(500, 10)

    def forward(self, x): 
        x = F.relu(self.conv1(x))
        x = F.max_pool2d(x, 2, 2)
        x = F.relu(self.conv2(x))
        x = F.max_pool2d(x, 2, 2)
        x = x.view(-1, 4 * 4 * 50)
        x = F.relu(self.fc1(x))
        x = self.fc2(x)
        return x

    def name(self):
        return "LeNet"

## training
model = LeNet()

optimizer = optim.SGD(model.parameters(), lr=0.01, momentum=0.9)

criterion = nn.CrossEntropyLoss()

for epoch in range(1):
    # trainning
    ave_loss = 0
    for batch_idx, (x, target) in enumerate(train_loader):
        optimizer.zero_grad()
        x, target = Variable(x), Variable(target)
        out = model(x)
        loss = criterion(out, target)
        ave_loss = (ave_loss * batch_idx + loss.item()) / (batch_idx + 1)
        loss.backward()
        optimizer.step()
        if (batch_idx + 1) % 100 == 0 or (batch_idx + 1) == len(train_loader):
            print(
                "==>>> epoch: {}, batch index: {}, train loss: {:.6f}".format(
                    epoch, batch_idx + 1, ave_loss
                )
            )
    # testing
    correct_cnt, total_cnt, ave_loss = 0, 0, 0
    for batch_idx, (x, target) in enumerate(test_loader):
        x, target = Variable(x, volatile=True), Variable(target, volatile=True)
        out = model(x)
        loss = criterion(out, target)
        _, pred_label = torch.max(out.data, 1)
        total_cnt += x.data.size()[0]
        correct_cnt += (pred_label == target.data).sum()
        ave_loss = (ave_loss * batch_idx + loss.item()) / (batch_idx + 1)

        if (batch_idx + 1) % 100 == 0 or (batch_idx + 1) == len(test_loader):
            print(
                "==>>> epoch: {}, batch index: {}, test loss: {:.6f}, acc: {:.3f}".format(
                    epoch, batch_idx + 1, ave_loss, correct_cnt * 1.0 / total_cnt
                )
            )

torch.save(model.state_dict(), model.name())

Καταγραφή μοντέλου με MLflow

Τώρα, ξεκινάτε μια εκτέλεση MLflow και παρακολουθείτε τα αποτελέσματα στο πείραμα εκμάθησης μηχανής.

with mlflow.start_run() as run:
    print("log pytorch model:")
    mlflow.pytorch.log_model(
        model, "pytorch-model", registered_model_name="sample-pytorch"
    )

    model_uri = "runs:/{}/pytorch-model".format(run.info.run_id)
    print("Model saved in run %s" % run.info.run_id)
    print(f"Model URI: {model_uri}")

Ο παραπάνω κώδικας δημιουργεί μια εκτέλεση με τις καθορισμένες παραμέτρους και καταγράφει την εκτέλεση εντός του πειράματος sample-pytorch. Αυτό το τμήμα κώδικα δημιουργεί ένα νέο μοντέλο που ονομάζεται δείγμα-pytorch.

Φόρτωση και αξιολόγηση του μοντέλου

Μετά την αποθήκευση του μοντέλου, μπορεί επίσης να φορτωθεί για συμπεραίτ.

# Inference with loading the logged model
loaded_model = mlflow.pytorch.load_model(model_uri)
print(type(loaded_model))

correct_cnt, total_cnt, ave_loss = 0, 0, 0
for batch_idx, (x, target) in enumerate(test_loader):
    x, target = Variable(x, volatile=True), Variable(target, volatile=True)
    out = loaded_model(x)
    loss = criterion(out, target)
    _, pred_label = torch.max(out.data, 1)
    total_cnt += x.data.size()[0]
    correct_cnt += (pred_label == target.data).sum()
    ave_loss = (ave_loss * batch_idx + loss.item()) / (batch_idx + 1)

    if (batch_idx + 1) % 100 == 0 or (batch_idx + 1) == len(test_loader):
        print(
            "==>>> epoch: {}, batch index: {}, test loss: {:.6f}, acc: {:.3f}".format(
                epoch, batch_idx + 1, ave_loss, correct_cnt * 1.0 / total_cnt
            )
        )