Contenu du cours
Essentiels de Pytorch
Essentiels de Pytorch
Entraînement du Modèle
Préparation pour l'entraînement
Tout d'abord, vous devez vous assurer que le modèle, la fonction de perte et l'optimiseur sont correctement définis. Passons en revue chaque étape :
- Fonction de perte : pour la classification, vous pouvez utiliser
CrossEntropyLoss
, qui attend des valeurs continues brutes (logits) en entrée et applique automatiquementsoftmax
; - Optimiseur : vous pouvez utiliser l'optimiseur Adam pour des mises à jour de gradient efficaces.
Dans PyTorch, la perte de cross-entropie combine log-softmax et perte de log-vraisemblance négative (NLL) en une seule fonction de perte :
où :
- zy est le logit correspondant à la classe correcte;
- C est le nombre total de classes.
Il est également important de diviser les données en ensembles d'entraînement et de validation (idéalement, un ensemble de test séparé devrait également exister). Étant donné que le jeu de données est relativement petit (1143 lignes), nous utilisons une répartition de 80% à 20%. Dans ce cas, l'ensemble de validation servira également d'ensemble de test.
De plus, les tableaux NumPy résultants doivent être convertis en tensors, car les modèles PyTorch nécessitent des entrées de tenseur pour les calculs.
Boucle d'entraînement
La boucle d'entraînement implique les étapes suivantes pour chaque époque :
- Passage avant : passer les caractéristiques d'entrée à travers le modèle pour générer des prédictions ;
- Calcul de la perte : comparer les prédictions avec la vérité terrain en utilisant la fonction de perte ;
- Passage arrière : calculer les gradients par rapport aux paramètres du modèle en utilisant la rétropropagation ;
- Mise à jour des paramètres : ajuster les paramètres du modèle en utilisant l'optimiseur ;
- Suivi des progrès : imprimer périodiquement la perte pour observer la convergence.
Comme vous pouvez le voir, le processus d'entraînement est similaire à celui de la régression linéaire.
import torch.nn as nn import torch import torch.optim as optim import matplotlib.pyplot as plt import os os.system('wget https://staging-content-media-cdn.codefinity.com/courses/1dd2b0f6-6ec0-40e6-a570-ed0ac2209666/section_3/model_definition.py 2>/dev/null') from model_definition import model, X, y from sklearn.model_selection import train_test_split # Set manual seed for reproducibility torch.manual_seed(42) # Reinitialize model after setting seed model.apply(lambda m: m.reset_parameters() if hasattr(m, "reset_parameters") else None) X_train, X_test, y_train, y_test = train_test_split(X, y, test_size=0.2, random_state=42) X_train = torch.tensor(X_train, dtype=torch.float32) X_test = torch.tensor(X_test, dtype=torch.float32) y_train = torch.tensor(y_train, dtype=torch.long) y_test = torch.tensor(y_test, dtype=torch.long) # Define the loss function (Cross-Entropy for multi-class classification) criterion = nn.CrossEntropyLoss() # Define the optimizer (Adam with a learning rate of 0.01) optimizer = optim.Adam(model.parameters(), lr=0.01) # Number of epochs epochs = 100 # Store losses for plotting training_losses = [] # Training loop for epoch in range(epochs): # Zero out gradients from the previous step optimizer.zero_grad() # Compute predictions predictions = model(X_train) # Compute the loss loss = criterion(predictions, y_train) # Compute gradients loss.backward() # Update parameters optimizer.step() # Store the loss training_losses.append(loss.item()) # Plot the training loss plt.plot(range(epochs), training_losses, label="Training Loss") plt.xlabel("Epoch") plt.ylabel("Loss") plt.title("Training Loss over Epochs") plt.legend() plt.show()
Observation de la convergence
En plus de l'entraînement du modèle, nous enregistrons également la perte d'entraînement à chaque époque et la traçons au fil du temps. Comme le montre le graphique, la perte d'entraînement diminue rapidement au début, puis se stabilise progressivement autour de l'époque 60. Au-delà de ce point, la perte diminue à un rythme beaucoup plus lent, ce qui suggère que le modèle a probablement convergé. Par conséquent, utiliser environ 40 époques pour ce modèle serait suffisant.
Merci pour vos commentaires !