Deep Learning Applicato con PyTorch (Da Zero a Maestro)
Questo corso offre un'introduzione completa al Deep Learning utilizzando PyTorch, il framework più popolare per la ricerca in campo di machine learning. Partendo dalle basi dei tensori, gli studenti percorreranno l'intero flusso di lavoro dell'apprendimento automatico, visione artificiale, ingegneria del software modulare, apprendimento transfer e deployment dei modelli. Il piano di studi è basato sul codice, con un'enfasi sulla realizzazione pratica e sperimentazione.
Panoramica del corso
📚 Riepilogo del contenuto
Questo corso offre un'introduzione completa all'Apprendimento Profondo con PyTorch, il framework più diffuso per la ricerca in campo machine learning. Partendo dalle basi dei tensori, gli studenti percorreranno l'intero flusso ML, visione artificiale, ingegneria software modulare, transfer learning e deployment dei modelli. Il curriculum è "code-first", con un'enfasi sulla pratica e sull'esperimentazione, garantendo che gli studenti non solo comprendano la teoria ma siano in grado di costruire, ottimizzare e distribuire sistemi profondi robusti.
Un breve riassunto degli obiettivi principali è padroneggiare l'intero ecosistema PyTorch, passando dalla matematica fondamentale a applicazioni di visione artificiale pronte per la produzione.
🎯 Obiettivi di apprendimento
- Implementare l'intero flusso di machine learning con PyTorch, dalle operazioni fondamentali sui tensori fino all'addestramento, alla valutazione e al persistere del modello.
- Progettare e distribuire architetture di deep learning, inclusi Reti Neurali Artificiali (ANN) e Reti Neurali Convolutionali (CNN), per compiti complessi di classificazione e visione artificiale.
- Trasformare il codice sperimentale in software modulare pronto per la produzione, adottando pratiche ingegneristiche standardizzate e strutture di directory.
- Utilizzare tecniche avanzate come il Transfer Learning e il tracciamento sistematico degli esperimenti (TensorBoard) per ottenere risultati all'avanguardia su dataset personalizzati.
- Preparare e distribuire modelli addestrati in applicazioni web interattive e sfruttare le funzionalità moderne di PyTorch 2.0 per accelerare l'inferenza.
🔹 Lezione 1: Fondamenti di PyTorch
Panoramica: Questa lezione fondamentale introduce PyTorch e la sua struttura dati principale: il tensore. Cominceremo spiegando perché PyTorch è il framework preferito per la ricerca moderna in ambito deep learning, enfatizzando il suo grafico computazionale dinamico. L'obiettivo tecnico centrale è padroneggiare la manipolazione dei tensori. Gli studenti impareranno a inizializzare tensori—da scalari 0D a matrici multidimensionali—utilizzando diverse metodologie (es. torch.zeros(), torch.rand()). Verranno trattate operazioni essenziali, tra cui aritmetica elementare (somma, moltiplicazione) e operazioni specializzate di algebra lineare come la moltiplicazione matriciale (torch.matmul). Affronteremo anche tecniche di gestione strutturale, come indicizzazione, slicing, ridimensionamento (.view(), .reshape()), e rimozione di dimensioni ridondanti (.squeeze()). Infine, affronteremo il concetto cruciale dell'utilizzo di dispositivi diversi (CPU vs GPU) tramite .to(), preparando gli studenti per calcoli accelerati nelle lezioni successive.
Risultati di apprendimento:
- Spiegare il ruolo dei tensori come struttura dati fondamentale nel deep learning e in PyTorch.
- Creare e inizializzare tensori PyTorch di diverse dimensioni (scalari, vettori, matrici) utilizzando metodi integrati.
- Eseguire operazioni standard sui tensori e operazioni specializzate come la moltiplicazione matriciale.
- Manipolare la struttura del tensore utilizzando tecniche di indicizzazione, slicing, ridimensionamento e compressione.
- Spostare i tensori in modo efficiente tra CPU e GPU per calcoli accelerati.
🔹 Lezione 2: Il flusso di PyTorch
Panoramica: Questa lezione stabilisce il flusso di base ripetibile di PyTorch implementando un modello di regressione lineare semplice da zero. Cominciamo con la preparazione dei dati, concentrandoci sulla generazione di dati sintetici e sulla suddivisione in insiemi di addestramento e test, enfatizzando l'importanza dell'allineamento del tipo di dato e del dispositivo (CPU/GPU). Successivamente definiamo l'architettura del modello ereditando correttamente da torch.nn.Module e implementando il metodo forward(). Il nucleo del flusso riguarda la scelta delle funzioni di perdita appropriate (es. nn.L1Loss per la regressione) e degli ottimizzatori (Gradient Descent Stocastico o SGD). Costruiremo poi attentamente il ciclo di addestramento (passata in avanti, calcolo della perdita, azzeramento dei gradienti, passata all'indietro, passo dell'ottimizzatore) e il ciclo di test/valutazione per misurare le prestazioni. Infine, concluderemo il framework imparando a salvare i dizionari di stato del modello addestrato tramite torch.save() e a ricaricarli successivamente per inferenza o riutilizzo, completando così tutto il ciclo end-to-end del ML.
Risultati di apprendimento:
- Strutturare e implementare i sei passaggi fondamentali del flusso di machine learning end-to-end di PyTorch.
- Costruire un modello lineare semplice definendo una classe che eredita correttamente da
torch.nn.Module. - Applicare funzioni di perdita appropriate (
nn.L1Loss) e ottimizzatori (torch.optim.SGD) per compiti di regressione basilari. - Definire ed eseguire il ciclo di addestramento, incluso il backpropagation e il gradiente discendente, e il ciclo di valutazione separato.
- Implementare la funzionalità per salvare e caricare i dizionari di stato del modello usando utility di PyTorch per la persistenza del modello.
🔹 Lezione 3: Classificazione con Reti Neurali
Panoramica: Questa lezione applica il flusso di PyTorch per risolvere problemi di classificazione non lineari, andando oltre la semplice regressione lineare. Cominciamo distinguendo tra scenari binari e multi-classe e dimostriamo come strutturare l'ultimo livello di output utilizzando attivazioni Sigmoid (per il binario) e Softmax (per il multi-classe). Viene introdotto il concetto cruciale della non linearità integrando funzioni di attivazione ReLU nei livelli nascosti, permettendo al modello di imparare confini decisionali complessi. Gli studenti implementeranno le funzioni di perdita corrette per la classificazione: BCEWithLogitsLoss e CrossEntropyLoss. La parte pratica consiste nella generazione e nell'addestramento di una rete neurale su un dataset sintetico complesso (es. il dataset 'moons') e nella visualizzazione del superficie decisionale risultante per confermare la capacità del modello di separare efficacemente punti dati non lineari, assicurando una padronanza delle architetture fondamentali dei modelli deep learning.
Risultati di apprendimento:
- Distinguere e implementare modelli PyTorch per compiti di classificazione binaria e multi-classe.
- Spiegare la necessità di funzioni di attivazione non lineari (ReLU, Sigmoid, Softmax) per abilitare confini decisionali complessi.
- Applicare funzioni di perdita appropriate (
BCEWithLogitsLoss,CrossEntropyLoss) e calcolare metriche di accuratezza per la classificazione. - Implementare l'intero flusso di classificazione PyTorch su un dataset non lineare.
- Visualizzare il confine decisionale appreso da un modello e interpretarne la capacità di classificare i punti dati.
🔹 Lezione 4: Visione Artificiale con CNNs
Panoramica: Questa sessione segna il passaggio critico dal trattamento di dati strutturati a quello di dati immagine ad alta dimensione, richiedendo architetture deep learning specializzate. Cominceremo smantellando la rappresentazione delle immagini come tensori PyTorch multidimensionali, concentrando l'attenzione sulla notazione standard delle forme (N, C, H, W: Dimensione del batch, Canali, Altezza, Larghezza). Il nucleo teorico introduce le Reti Neurali Convolutionali (CNN) spiegando come i livelli convoluzionali (nn.Conv2d) estraggono in modo efficiente caratteristiche spaziali locali, e come i livelli di pooling (nn.MaxPool2d) riducono la dimensionalità preservando informazioni importanti. Attraverso un approccio code-first, costruiremo e addestreremo un'architettura CNN completa e di piccole dimensioni—una replica TinyVGG—da zero, fornendo un esempio pratico di un modello di visione artificiale funzionante. Infine, confrontiamo le differenze fondamentali tra questa struttura CNN e le reti lineari usate precedentemente per consolidare l'intuizione sul perché le CNN eccellano nel riconoscimento di pattern nelle immagini.
Risultati di apprendimento:
- Spiegare e utilizzare il formato tensore (N, C, H, W) per rappresentare i dati immagine in PyTorch.
- Implementare livelli Convolutionali (nn.Conv2d) e di Pooling (nn.MaxPool2d) all'interno di un modello PyTorch.
- Costruire e addestrare un'architettura CNN completa e di piccole dimensioni (una replica TinyVGG) per un compito di classificazione.
- Articolare le differenze fondamentali nell'estrazione delle caratteristiche e nelle capacità di condivisione dei pesi tra i livelli lineari e le CNN.
🔹 Lezione 5: Dataset Personalizzati
Panoramica: Questa sessione cruciale colma il divario tra esempi strutturati (come MNIST) e dati immagine reali complessi e non strutturati, preparando il terreno per il progetto pratico "FoodVision" di visione artificiale. Cominceremo imparando a strutturare correttamente le directory dei dati per PyTorch, utilizzando la classe estremamente efficiente torchvision.datasets.ImageFolder per caricare automaticamente i dati e dedurre i label dai percorsi dei file. In modo cruciale, padronizzeremo il concetto della classe personalizzata torch.utils.data.Dataset, che fornisce un controllo completo sulla logica di caricamento dei dati, sul pre-processing e sulla gestione dei label per formati di dati arbitrari. Introdurremo poi DataLoader per gestire il caricamento efficiente dei batch, il mescolamento e il caricamento multithread. Infine, la sessione copre tecniche essenziali di augmentation dei dati e trasformazioni di PyTorch, vitali per espandere la dimensione effettiva di dataset limitati e migliorare la generalizzazione e la robustezza del modello.
Risultati di apprendimento:
- Strutturare dati immagine reali nella formattazione di directory prevista dagli strumenti di PyTorch.
- Utilizzare
torchvision.datasets.ImageFolderper caricare in modo efficiente dataset immagine personalizzati dal disco. - Implementare una classe personalizzata
torch.utils.data.Datasetper gestire requisiti di caricamento dati unici o complessi. - Applicare una gamma di
torchvision.transformsper il pre-processing (ridimensionamento, conversione in tensore) e l'aumentazione dei dati (rotazione, riflessione). - Integrare la classe
DatasetconDataLoaderper gestire batching, mescolamento e caricamento parallelo ottimizzato.
🔹 Lezione 6: Diventare Modulare (Ingegneria Software)
Panoramica: Questa sessione è cruciale per passare dal codice sperimentale di Jupyter Notebook a pratiche di ingegneria software sostenibili e pronte per la produzione all'interno dell'ecosistema PyTorch. Copriremo i passaggi obbligatori per rifattorizzare il codice monolitico dei notebook in script Python strutturati e riutilizzabili. Il concetto centrale consiste nell'istituire una struttura standardizzata per progetti PyTorch, separando le responsabilità in moduli dedicati. I moduli chiave da creare includono data_setup.py (gestione del caricamento dei dati, trasformazioni e DataLoaders), model_builder.py (contenente le definizioni dei modelli che ereditano da nn.Module) e engine.py (gestione dei cicli di addestramento e test). Infine, gli studenti impareranno come inizializzare ed eseguire l'intero processo di addestramento direttamente dalla riga di comando utilizzando l'esecuzione standard di Python, essenziale per il deployment e gli esperimenti su larga scala.
Risultati di apprendimento:
- Spiegare le differenze tra il codice sperimentale dei notebook e l'architettura strutturata e modulare di script Python.
- Implementare una struttura standardizzata per progetti PyTorch pensata per scalabilità e collaborazione.
- Rifattorizzare la logica esistente di addestramento del modello in moduli distinti e riutilizzabili (es. data_setup.py, model_builder.py, engine.py).
- Configurare uno script principale per eseguire l'intero processo di addestramento dalla linea di comando.
- Descrivere i benefici pratici del codice modulare in termini di test, controllo versione e prontezza per il deployment in produzione.
🔹 Lezione 7: Transfer Learning
Panoramica: Il Transfer Learning è una tecnica potente che ci permette di sfruttare conoscenze acquisite da modelli addestrati su grandi dataset, come ImageNet, applicandole in modo efficiente a problemi più piccoli e specializzati. Questa sessione introduce la teoria fondamentale, enfatizzando perché i pesi pre-addestrati (specificamente da modelli come ResNet o EfficientNet tramite torchvision.models) sono cruciali per ottenere risultati all'avanguardia con meno dati e tempi di calcolo ridotti. L'implementazione pratica si concentra sul Feature Extraction: gli studenti impareranno a caricare un modello, a bloccare i parametri dei suoi livelli base convoluzionali usando requires_grad=False di PyTorch, e quindi a sostituire e addestrare solo la testa finale di classificazione personalizzata per un nuovo dominio target, come il progetto in corso "FoodVision". Confronteremo poi questo metodo con l'approccio più costoso in termini di calcolo del Fine-tuning di tutta la rete.
Risultati di apprendimento:
- Spiegare il vantaggio teorico e i casi comuni in cui il Transfer Learning è necessario.
- Caricare e ispezionare architetture di modelli pre-addestrati comuni usando l'utilità
torchvision.modelsdi PyTorch. - Implementare il Feature Extraction bloccando con successo i parametri dei livelli convoluzionali di base.
- Modificare la testa del classificatore di un modello pre-addestrato per gestire nuovi compiti di classificazione personalizzati.
- Differenziare tra strategie di Feature Extraction (blocco) e Fine-Tuning (sblocco).
🔹 Lezione 8: Tracciamento degli Esperimenti (Progetto Milestone 1)
Panoramica: Man mano che passiamo dal training di singoli modelli a confronti sofisticati (es. confrontare una CNN vanilla con un modello di Transfer Learning), il logging manuale diventa insufficiente. Questa lezione stabilisce la pratica cruciale del tracciamento sistematico degli esperimenti. Introdurremo e implementeremo la soluzione nativa di PyTorch, torch.utils.tensorboard.SummaryWriter, per registrare e gestire i dati di prestazione. Gli studenti impareranno a strumentare i loro cicli di addestramento per registrare metriche scalari fondamentali, come la perdita di addestramento e test per ogni epoca, l'accuratezza e i tassi di apprendimento. L'obiettivo principale è padroneggiare l'avvio e l'utilizzo dell'interfaccia TensorBoard per confrontare visivamente i risultati di più run in parallelo, consentendo un'analisi oggettiva dei cambiamenti negli iperparametri, delle decisioni architetturali e delle strategie di ottimizzazione, garantendo così riproducibilità e accelerando il miglioramento del modello.
Risultati di apprendimento:
- Spiegare la necessità di un tracciamento sistematico degli esperimenti per garantire riproducibilità e efficienza nel deep learning.
- Implementare la classe
torch.utils.tensorboard.SummaryWriterper registrare metriche scalari (perdita, accuratezza) all'interno di un ciclo di addestramento PyTorch. - Avviare e navigare l'interfaccia TensorBoard per visualizzare curve metriche e confrontare le prestazioni di diverse esecuzioni sperimentali.
- Applicare tecniche di tracciamento per confrontare sistematicamente l'impatto di impostazioni diverse di iperparametri (es. dimensione del batch, tasso di apprendimento) e architetture di modello.
🔹 Lezione 9: Replica di Articoli Scientifici (Progetto Milestone 2)
Panoramica: Questa lezione rappresenta l'apice del corso, sfidando gli studenti a tradurre la ricerca teorica in codice funzionale replicando un'architettura moderna da un articolo scientifico. Cominceremo a smantellare la struttura di un articolo ML tipico, focalizzandoci specificamente su come estrarre dettagli architetturali e formulazioni matematiche dalla sezione Metodologia. Il compito tecnico centrale consiste nel mappare equazioni matematiche complesse—come quelle che governano meccanismi di attenzione o tipi di layer innovativi—direttamente in moduli PyTorch utilizzando classi nn.Module personalizzate. Un esempio moderno, come il Vision Transformer (ViT), sarà utilizzato come caso studio per l'implementazione. L'accento sarà posto su strategie sistematiche di debugging richieste per modelli complessi a più componenti, affrontando sfide come compatibilità delle forme, inizializzazione dei pesi e verifica del flusso dei gradienti, assicurando che gli studenti possano implementare con successo modelli all'avanguardia da zero.
Risultati di apprendimento:
- Deconstruire e analizzare le descrizioni architetturali e le notazioni matematiche presenti negli articoli di ricerca sul deep learning.
- Tradurre passaggi algoritmici complessi e formule (es. meccanismi di self-attention) direttamente in codice PyTorch idiomatico utilizzando classi
nn.Modulepersonalizzate. - Implementare e integrare tutti i componenti richiesti di un'architettura moderna e complessa di deep learning (es. Vision Transformer) completamente da zero.
- Applicare strategie di debugging avanzate per risolvere errori di forma, discrepanze di dispositivo e difetti logici incontrati durante la replica di modelli all'avanguardia.
🔹 Lezione 10: Deployment dei Modelli e PyTorch 2.0
Panoramica: Questa ultima lezione si concentra sul transizione di un modello PyTorch addestrato dall'ambiente di ricerca a un'applicazione web interattiva pubblica. Cominceremo imparando i passaggi cruciali per preparare un modello al deployment, focalizzandoci sul caricamento efficiente e sull'inferenza per la produzione. L'attività principale pratica consiste nel creare una demo funzionale web utilizzando strumenti di prototipazione rapida come Gradio o Streamlit, permettendo agli utenti finali di inserire dati e ricevere previsioni immediate. Copriremo strategie pratiche per ospitare queste applicazioni, sfruttando piattaforme come Hugging Face Spaces. Infine, dedicheremo tempo all'esplorazione del futuro del framework, in particolare alle migliorie prestazionali e alle funzionalità di compilazione introdotte in PyTorch 2.0, dimostrando come innovazioni come torch.compile offrano notevoli velocizzazioni sia per l'addestramento che per il deployment.
Risultati di apprendimento:
- Preparare un artefatto di modello PyTorch addestrato per un caricamento e un'inferenza efficienti in produzione.
- Sviluppare un'interfaccia web funzionale e interattiva utilizzando Gradio o Streamlit.
- Ospitare l'applicazione di machine learning sviluppata su una piattaforma pubblica (es. Hugging Face Spaces).
- Spiegare il concetto centrale e il meccanismo della funzione
torch.compileintrodotta in PyTorch 2.0. - Integrare la conoscenza sul deployment con le pratiche precedenti di codice modulare per creare un progetto finale end-to-end.