projet-8-api / guide_projet_8.md
JeanProjets's picture
Upload folder using huggingface_hub
d777431 verified
|
Raw
History Blame Contribute Delete
25.2 kB
# Guide Complet — Projet 8 : Déploiement d'un Modèle de Segmentation d'Images
> **Contexte** : Tu es ingénieur IA chez *Future Vision Transport*. Tu conçois le module de **segmentation d'images** dans une chaîne de vision embarquée pour véhicules autonomes. Le dataset est **Cityscapes**, le framework imposé est **Keras**, et tu dois livrer un modèle + API + application web déployés sur le Cloud.
---
## Phase 0 — Mise en place de l'environnement
### 0.1 Créer un environnement virtuel Python dédié
```bash
python -m venv venv_projet8
source venv_projet8/bin/activate
pip install tensorflow keras numpy pandas matplotlib opencv-python albumentations flask fastapi uvicorn streamlit
```
- **Why** : Isoler les dépendances évite les conflits entre projets. C'est une pratique professionnelle standard.
- **Notions** : *virtual environments*, gestion de dépendances avec `pip`, `requirements.txt`.
### 0.2 Structurer le répertoire de travail
```
Projet_8/
├── data/ # Données Cityscapes (déjà présent)
├── notebooks/ # Notebooks d'exploration et d'entraînement
├── src/ # Code source réutilisable (data generator, model, utils)
├── api/ # Code de l'API Flask/FastAPI
├── app/ # Code de l'application web Streamlit/Flask
├── models/ # Modèles sauvegardés (.h5, .keras)
├── docs/ # Note technique + supports de présentation
└── requirements.txt
```
- **Why** : Une structure claire rend le projet "industrialisable" (critère évalué dans les livrables) et facilite la collaboration.
- **Notions** : *project scaffolding*, bonnes pratiques d'organisation de projets ML.
### 0.3 Initialiser un dépôt Git
```bash
git init
echo "venv_projet8/\ndata/\nmodels/*.h5\n__pycache__/" > .gitignore
```
- **Why** : Le versionnement est indispensable pour tracer l'évolution du code, revenir en arrière, et montrer ta démarche.
- **Notions** : *Git*, versionnement, `.gitignore`.
---
## Phase 1 — Comprendre les données Cityscapes
### 1.1 Télécharger le jeu de données complet
> **Observation** : Ton dossier [data/](file:///Users/j/Documents/OC_Inge_IA/Projet_8/data) contient actuellement uniquement les **annotations gtFine** (masks de segmentation), pas les images brutes. Tu dois télécharger les images `leftImg8bit` depuis [cityscapes-dataset.com](https://www.cityscapes-dataset.com/).
- **Why** : Ton modèle prend en entrée les **images caméra** (leftImg8bit) et doit prédire les **masks de segmentation** (gtFine). Sans les images, tu ne peux pas entraîner.
- **Notions** : *supervised learning*, notion d'images d'entrée vs. ground truth / labels.
### 1.2 Comprendre la structure des fichiers
Pour chaque image, Cityscapes fournit :
| Fichier | Description |
|---------|-------------|
| `*_leftImg8bit.png` | Image caméra brute (1024×2048) |
| `*_gtFine_labelIds.png` | Mask avec label ID par pixel (0-33) |
| `*_gtFine_color.png` | Mask coloré (visualisation) |
| `*_gtFine_instanceIds.png` | Mask d'instances |
| `*_gtFine_polygons.json` | Annotations polygonales |
- **Why** : Comprendre ce que chaque fichier représente est crucial avant de construire ton pipeline de données. Tu utiliseras principalement `leftImg8bit` + `labelIds`.
- **Notions** : *semantic segmentation*, *instance segmentation*, label maps, correspondance pixel-classe.
### 1.3 Comprendre les 8 catégories principales vs les 32 sous-catégories
Le projet demande de travailler avec les **8 catégories principales** :
| ID Cat. | Catégorie | Sous-catégories incluses |
|---------|-----------|-------------------------|
| 0 | **void** | unlabeled, ego vehicle, rectification border, out of roi, static, dynamic |
| 1 | **flat** | road, sidewalk, parking, rail track |
| 2 | **construction** | building, wall, fence, guard rail, bridge, tunnel |
| 3 | **object** | pole, polegroup, traffic light, traffic sign |
| 4 | **nature** | vegetation, terrain |
| 5 | **sky** | sky |
| 6 | **human** | person, rider |
| 7 | **vehicle** | car, truck, bus, caravan, trailer, train, motorcycle, bicycle |
- **Why** : C'est une contrainte explicite du projet (Franck). Tu dois mapper les 32 sous-catégories vers ces 8. Cela simplifie le problème et rend le modèle plus robuste.
- **Notions** : *label remapping*, *category grouping*, dictionnaire de correspondance Cityscapes.
### 1.4 Explorer visuellement les données (EDA)
Dans un notebook, afficher côte à côte :
- L'image brute
- Le mask coloré (`gtFine_color`)
- Le mask labelIds remappé vers les 8 catégories
- Distribution des classes par image (histogrammes)
- **Why** : L'EDA permet de détecter le *class imbalance* (par exemple, "road" et "building" dominent, "rider" est rare). Cela guidera tes choix d'augmentation de données et de loss function.
- **Notions** : *Exploratory Data Analysis*, *class imbalance*, visualisation de masks de segmentation, `matplotlib.imshow()`.
---
## Phase 2 — État de l'Art et Recherche Bibliographique
### 2.1 Étudier les architectures de segmentation sémantique
Architectures incontournables à comprendre et comparer :
| Architecture | Principe clé | Avantage |
|-------------|--------------|----------|
| **FCN** (Fully Convolutional Network) | Remplace les couches FC par des convolutions | Premier modèle end-to-end pour la segmentation |
| **U-Net** | Encoder-decoder avec skip connections | Excellent pour les détails fins, idéal pour les données limitées |
| **SegNet** | Encoder-decoder avec pooling indices | Plus léger en mémoire que U-Net |
| **DeepLab v3+** | Atrous convolutions + ASPP + encoder-decoder | State-of-the-art, capture multi-échelle |
| **PSPNet** | Pyramid Pooling Module | Capture le contexte global |
- **Why** : La note technique demande une "présentation des différentes approches et une synthèse de l'état de l'art". Tu dois comprendre les forces/faiblesses de chaque architecture pour justifier ton choix.
- **Notions** : *encoder-decoder architecture*, *skip connections*, *atrous/dilated convolutions*, *feature pyramid*, *receptive field*.
### 2.2 Étudier les métriques de segmentation
| Métrique | Formule/Description |
|----------|-------------------|
| **Pixel Accuracy** | % de pixels correctement classifiés |
| **Mean IoU (mIoU)** | Intersection over Union moyenné sur toutes les classes |
| **Dice Coefficient** | 2×TP / (2×TP + FP + FN) |
| **Per-class IoU** | IoU calculé pour chaque classe individuellement |
- **Why** : Le pixel accuracy est trompeur sur des données déséquilibrées. Le mIoU est la métrique standard en segmentation sémantique et sera celle que l'évaluateur attend.
- **Notions** : *IoU (Intersection over Union)*, *Dice score*, *confusion matrix* pixel-level, *mean IoU*.
### 2.3 Étudier les loss functions adaptées
- **Categorical Cross-Entropy** : Standard, mais sensible au class imbalance
- **Weighted Cross-Entropy** : Pondération inversement proportionnelle à la fréquence de la classe
- **Dice Loss** : Optimise directement le Dice Coefficient
- **Focal Loss** : Réduit la contribution des exemples bien classifiés
- **Combinaison** : Dice Loss + Cross-Entropy souvent utilisée en pratique
- **Why** : Le choix de la loss function a un impact direct sur les performances, surtout avec des classes déséquilibrées (road vs rider).
- **Notions** : *loss functions*, *class weighting*, *focal loss*, *dice loss*.
---
## Phase 3 — Pipeline de Données
### 3.1 Créer un Data Generator Keras
```python
class CityscapesGenerator(tf.keras.utils.Sequence):
def __init__(self, image_paths, mask_paths, batch_size, img_size, augment=False):
...
def __getitem__(self, idx):
# Charge batch d'images + masks
# Remapping 32 → 8 catégories
# Resize
# Augmentation (si train)
# One-hot encoding du mask
...
```
- **Why** : Les images Cityscapes (1024×2048) sont trop volumineuses pour tout charger en RAM. Un generator charge les données par batch à la volée. C'est un critère du livrable ("caractère industrialisable").
- **Notions** : `tf.keras.utils.Sequence`, *batch loading*, *lazy loading*, *one-hot encoding* de masks, *yield* vs *return*.
### 3.2 Implémenter le label remapping (32 → 8 catégories)
```python
# Dictionnaire de mapping utilisant la documentation Cityscapes
LABEL_TO_CATEGORY = {
0: 0, 1: 0, 2: 0, 3: 0, 4: 0, 5: 0, 6: 0, # void
7: 1, 8: 1, 9: 1, 10: 1, # flat
11: 2, 12: 2, 13: 2, 14: 2, 15: 2, 16: 2, # construction
17: 3, 18: 3, 19: 3, 20: 3, # object
21: 4, 22: 4, # nature
23: 5, # sky
24: 6, 25: 6, # human
26: 7, 27: 7, 28: 7, 29: 7, 30: 7, 31: 7, 32: 7, 33: 7 # vehicle
}
```
- **Why** : Franck (le collègue en charge du traitement d'images) a spécifié que seules les 8 catégories principales sont nécessaires. Ce remapping doit être fait dans le pipeline de données, pas manuellement.
- **Notions** : *label encoding*, *numpy vectorized mapping* (`np.vectorize` ou table de lookup), correspondance Cityscapes.
### 3.3 Implémenter l'augmentation de données
Techniques à appliquer :
- **Flip horizontal** (le plus commun pour la conduite)
- **Rotation légère** (±10°)
- **Variations de luminosité/contraste**
- **Random crop + resize**
- **Ajout de bruit gaussien**
> L'augmentation doit être appliquée **identiquement** à l'image ET au mask !
- **Why** : Le livrable demande explicitement des "gains obtenus avec les approches d'augmentation des données". L'augmentation permet de régulariser le modèle et d'augmenter virtuellement la taille du dataset.
- **Notions** : *data augmentation*, bibliothèque `albumentations` (applique les mêmes transformations géométriques à l'image et au mask), *overfitting prevention*.
### 3.4 Gérer le redimensionnement des images
Réduire les images de 1024×2048 à une taille gérable :
- **256×512** : bon compromis vitesse/qualité pour les premiers tests
- **512×1024** : meilleure résolution si ressources GPU suffisantes
- **Why** : Les images originales sont très grandes. Entraîner en pleine résolution nécessite un GPU puissant (32+ Go VRAM). Le redimensionnement est un compromis nécessaire.
- **Notions** : *image resizing*, interpolation bilinéaire vs nearest-neighbor (pour les masks !), *aspect ratio preservation*.
---
## Phase 4 — Entraînement du Modèle
### 4.1 Commencer avec un modèle simple (baseline)
Entraîner un U-Net simple depuis zéro comme baseline :
- Encoder : blocs Conv2D + BatchNorm + ReLU + MaxPool
- Decoder : UpSampling2D + Concatenate (skip connections) + Conv2D
- Sortie : Conv2D(8, (1,1), activation='softmax')
- **Why** : Un modèle simple permet de valider que tout le pipeline fonctionne (data loading, training loop, évaluation) avant d'investir du temps dans des architectures plus complexes.
- **Notions** : *U-Net architecture*, *encoder-decoder*, *skip connections*, *softmax pour classification multi-classe pixel-level*.
### 4.2 Utiliser le Transfer Learning
Utiliser un backbone pré-entraîné sur ImageNet :
- **MobileNetV2** : léger, idéal pour l'embarqué
- **ResNet50** : bon compromis performance/poids
- **EfficientNet** : état de l'art en efficacité
```python
base_model = tf.keras.applications.MobileNetV2(input_shape=(256, 512, 3), include_top=False, weights='imagenet')
```
- **Why** : Le transfer learning permet d'obtenir de bien meilleures performances avec moins de données et moins de temps d'entraînement. Les features bas-niveau (contours, textures) apprises sur ImageNet sont transférables.
- **Notions** : *transfer learning*, *feature extraction vs fine-tuning*, *backbone freezing/unfreezing*, `keras.applications`.
### 4.3 Implémenter un modèle avancé (DeepLab v3+ ou similaire)
Options :
- Utiliser `segmentation_models` library : `pip install segmentation-models`
- Implémenter DeepLab v3+ manuellement avec Keras
- Utiliser TensorFlow Hub pour charger un modèle pré-entraîné
- **Why** : La comparaison entre un modèle simple (baseline) et un modèle avancé est attendue dans la note technique. DeepLab v3+ est souvent le meilleur choix pour Cityscapes.
- **Notions** : *ASPP (Atrous Spatial Pyramid Pooling)*, *dilated convolutions*, *multi-scale feature extraction*.
### 4.4 Configurer l'entraînement
```python
model.compile(
optimizer=tf.keras.optimizers.Adam(learning_rate=1e-4),
loss='categorical_crossentropy', # ou dice_loss + CE combinée
metrics=['accuracy', MeanIoU(num_classes=8)]
)
callbacks = [
tf.keras.callbacks.ModelCheckpoint('best_model.keras', save_best_only=True, monitor='val_mean_iou', mode='max'),
tf.keras.callbacks.EarlyStopping(patience=10, monitor='val_mean_iou', mode='max'),
tf.keras.callbacks.ReduceLROnPlateau(factor=0.5, patience=5),
tf.keras.callbacks.TensorBoard(log_dir='./logs')
]
```
- **Why** : Les callbacks automatisent la sauvegarde du meilleur modèle, l'arrêt précoce (évite l'overfitting), et l'ajustement du learning rate. C'est une démarche professionnelle.
- **Notions** : *callbacks Keras*, *early stopping*, *learning rate scheduling*, *model checkpointing*, *TensorBoard*.
### 4.5 Entraîner et comparer les modèles
Pour chaque modèle, documenter :
- Architecture utilisée
- Hyperparamètres (lr, batch size, epochs, augmentation)
- Courbes train/val loss et mIoU
- Per-class IoU sur le validation set
- Prédictions visuelles (image / ground truth / prédiction)
- **Why** : La soutenance demande la "comparaison des modèles" (10 min dédiées). Tu dois montrer une démarche itérative et justifier le modèle final retenu.
- **Notions** : *hyperparameter tuning*, *learning curves analysis*, *overfitting vs underfitting diagnosis*, *model selection*.
### 4.6 Évaluer sur le jeu de test
Calculer les métriques finales sur le test set (Berlin, Bielefeld, Bonn, Leverkusen, Mainz, Munich) :
- mIoU global
- IoU par classe
- Matrice de confusion pixel-level
- Visualisations qualitatives
- **Why** : L'évaluation sur le test set (jamais vu pendant l'entraînement) donne une estimation non biaisée des performances. C'est la norme en ML.
- **Notions** : *train/val/test split*, *generalization*, *qualitative vs quantitative evaluation*.
---
## Phase 5 — Développement de l'API de Prédiction
### 5.1 Choisir entre Flask et FastAPI
| Critère | Flask | FastAPI |
|---------|-------|---------|
| Facilité | Plus simple | Async concepts |
| Performance | Synchrone | Asynchrone natif |
| Documentation auto | | Swagger/OpenAPI inclus |
| Typing | | Pydantic intégré |
> **Recommandation** : FastAPI — la doc auto est un vrai plus pour Laura et la soutenance.
- **Why** : Laura veut une "API simple à utiliser". FastAPI génère automatiquement une documentation interactive (Swagger UI) qui permet de tester l'API sans code client.
- **Notions** : *REST API*, *endpoints*, *HTTP methods* (POST), *content types* (multipart/form-data, JSON).
### 5.2 Concevoir l'endpoint de prédiction
```python
from fastapi import FastAPI, File, UploadFile
import numpy as np
from PIL import Image
import io
app = FastAPI(title="Cityscapes Segmentation API")
# Charger le modèle au démarrage
model = tf.keras.models.load_model('best_model.keras')
@app.post("/predict")
async def predict(file: UploadFile = File(...)):
# 1. Lire l'image uploadée
image = Image.open(io.BytesIO(await file.read()))
# 2. Prétraiter (resize, normalisation)
# 3. Prédire le mask
# 4. Post-traiter (argmax, resize au format original)
# 5. Retourner le mask (encodé en base64 ou en JSON)
return {"mask": mask_as_list, "classes": class_names}
```
- **Why** : Cet endpoint est le cœur du livrable 2. Il prend une image et retourne le mask prédit. Il sera consommé par l'application web (livrable 3).
- **Notions** : *API endpoint design*, *image I/O* (bytes → PIL → numpy), *model inference pipeline*, *base64 encoding*.
### 5.3 Ajouter des endpoints utilitaires
- `GET /` : Infos sur l'API (version, modèle utilisé, classes)
- `GET /health` : Health check
- `GET /classes` : Liste des 8 catégories et leurs couleurs
- **Why** : Des endpoints d'information facilitent l'intégration et le monitoring. C'est une bonne pratique d'architecture API.
- **Notions** : *API design patterns*, *health checks*, *API versioning*.
### 5.4 Tester l'API en local
```bash
uvicorn api.main:app --reload --host 0.0.0.0 --port 8000
# Tester sur http://localhost:8000/docs (Swagger UI)
```
- **Why** : Toujours tester en local avant de déployer. La Swagger UI permet de tester visuellement l'upload d'image et la réponse.
- **Notions** : *local development server*, *API testing*, *Swagger/OpenAPI*.
---
## Phase 6 — Développement de l'Application Web
### 6.1 Concevoir l'application Streamlit (ou Flask)
L'application doit permettre :
1. **Afficher la liste des IDs** des images disponibles (test set)
2. **Sélectionner un ID** → lancer la prédiction via l'API
3. **Afficher 3 images côte à côte** : image réelle | mask réel | mask prédit
```python
import streamlit as st
import requests
st.title("Segmentation d'Images - Future Vision Transport")
# Liste des images disponibles
image_ids = get_available_image_ids()
selected_id = st.selectbox("Sélectionner une image :", image_ids)
if st.button("Lancer la prédiction"):
# Appel à l'API
response = requests.post(API_URL + "/predict", files={"file": image_bytes})
predicted_mask = decode_response(response.json())
col1, col2, col3 = st.columns(3)
col1.image(original_image, caption="Image réelle")
col2.image(ground_truth_mask, caption="Mask réel")
col3.image(predicted_mask, caption="Mask prédit")
```
- **Why** : Cette application est l'interface de démonstration (livrable 3). Elle doit consommer l'API, pas faire la prédiction directement — cela prouve que l'architecture est bien découplée.
- **Notions** : *Streamlit*, *API consumption* (`requests`), *image display*, *UI/UX pour une démo*, *client-server architecture*.
### 6.2 Ajouter des fonctionnalités bonus
- Palette de couleurs pour les classes (légende)
- Overlay du mask sur l'image originale (transparence)
- Métriques affichées (IoU par classe vs ground truth)
- Upload d'une image personnelle (pas du dataset)
- **Why** : Ces fonctionnalités impressionnent l'évaluateur et montrent une maîtrise au-delà du minimum requis.
- **Notions** : *image compositing*, *alpha blending*, *color mapping*.
---
## Phase 7 — Déploiement sur le Cloud
### 7.1 Choisir une plateforme Cloud
| Plateforme | Coût | Difficulté | GPU |
|-----------|------|-----------|-----|
| **Render** | Gratuit (limité) | ⭐⭐ | |
| **Railway** | Gratuit ($5 crédit) | ⭐⭐ | |
| **Azure Web App** | Free tier disponible | ⭐⭐⭐ | Option payante |
| **Google Cloud Run** | Free tier généreux | ⭐⭐⭐ | |
| **PythonAnywhere** | Gratuit (très limité) | ⭐ | |
| **AWS (EC2/Lambda)** | Free tier 12 mois | ⭐⭐⭐⭐ | Option payante |
- **Why** : Le déploiement Cloud est obligatoire pour la soutenance. Tu dois faire une démo en live et l'enregistrer. Choisis en fonction de ton budget et de ta familiarité.
- **Notions** : *cloud deployment*, *PaaS vs IaaS*, *containerization concepts*.
### 7.2 Containeriser avec Docker
```dockerfile
# API
FROM python:3.10-slim
WORKDIR /app
COPY requirements.txt .
RUN pip install --no-cache-dir -r requirements.txt
COPY . .
EXPOSE 8000
CMD ["uvicorn", "main:app", "--host", "0.0.0.0", "--port", "8000"]
```
- **Why** : Docker garantit que l'environnement est identique en local et en production. La plupart des plateformes Cloud supportent Docker nativement.
- **Notions** : *Docker*, *Dockerfile*, *containers vs VMs*, *image build*, *port mapping*.
### 7.3 Déployer l'API et l'application
Deux déploiements séparés :
1. **API** : déploiement du service de prédiction
2. **App web** : déploiement de l'interface Streamlit (pointe vers l'URL de l'API)
- **Why** : Séparer l'API de l'application web est une architecture microservices. Cela prouve la modularité de ton système.
- **Notions** : *microservices architecture*, *environment variables* pour l'URL de l'API, *CORS configuration*.
### 7.4 Enregistrer la démo pendant la soutenance
> **Important** : Le sujet précise que l'évaluateur et l'étudiant doivent **enregistrer la démo** pendant la soutenance pour que le jury puisse la visionner. Tu pourras ensuite couper le service Cloud pour éviter les coûts.
- **Why** : C'est une exigence explicite du sujet. Prépare un outil d'enregistrement d'écran (OBS, QuickTime, etc.).
- **Notions** : *screen recording*, préparation de démo.
---
## Phase 8 — Rédaction de la Note Technique (~10 pages)
### 8.1 Structure recommandée
| Section | Contenu | ~Pages |
|---------|---------|--------|
| **1. Introduction** | Contexte (Future Vision Transport), objectifs, contraintes | 1 |
| **2. État de l'Art** | Revue des architectures (FCN, U-Net, SegNet, DeepLab), métriques | 2 |
| **3. Dataset et Préparation** | Cityscapes, 8 catégories, EDA, augmentation | 1.5 |
| **4. Modèle Retenu** | Architecture détaillée, hyperparamètres, justification du choix | 2 |
| **5. Résultats** | Comparaison des modèles, mIoU, courbes, gains de l'augmentation | 2 |
| **6. Mise en Production** | Architecture API + App, déploiement Cloud | 1 |
| **7. Conclusion** | Bilan, limites, pistes d'amélioration | 0.5 |
- **Why** : La note technique est un livrable clé (livrable 4). Elle doit démontrer ta rigueur scientifique et ta capacité à synthétiser.
- **Notions** : *technical writing*, *scientific methodology*, *results presentation*.
### 8.2 Points clés à inclure
- **Comparaison explicite** des modèles (tableau mIoU)
- **Gains de l'augmentation** : comparer modèle sans augmentation vs avec
- **Visualisations** : courbes de loss, exemples de prédictions, matrice de confusion
- **Pistes d'amélioration** : Real-time inference, quantization, pruning, TensorRT
- **Why** : Ces éléments sont explicitement demandés dans le descriptif des livrables.
- **Notions** : *ablation study*, *model comparison*, *scientific rigor*.
---
## Phase 9 — Support de Présentation (max 30 slides)
### 9.1 Structure calquée sur le timing de soutenance
| Bloc | Durée | Slides | Contenu |
|------|-------|--------|---------|
| **Contexte & Objectifs** | 5 min | 5-7 | Entreprise, chaîne de vision, ton rôle, métriques |
| **Modèles & Résultats** | 10 min | 12-15 | Architectures, comparaisons, visualisations, augmentation |
| **Mise en Production** | 5 min | 5-8 | Architecture API/App, déploiement, démo live |
- **Why** : La soutenance est strictement chronométrée (20 min ±5). Une présentation trop courte (<15 min) ou trop longue (>25 min) peut être refusée.
- **Notions** : *presentation skills*, *storytelling technique*, *demo preparation*.
### 9.2 Préparer la démo live
Préparer un script de démo :
1. Ouvrir l'application web déployée
2. Sélectionner une image du test set
3. Lancer la prédiction
4. Montrer image / mask réel / mask prédit côte à côte
5. Éventuellement tester avec une image uploadée
> Tester la démo **plusieurs fois avant** la soutenance !
- **Why** : La démo est le moment fort de la soutenance. Un bug en live est très pénalisant. Prépare aussi des screenshots de backup au cas où le Cloud tombe.
- **Notions** : *demo rehearsal*, *fallback plan*.
---
## Checklist des Livrables
| # | Livrable | Format | Nommage |
|---|----------|--------|---------|
| 1 | **Scripts/Notebooks** (pipeline complet) | `.ipynb` / `.py` | `Nom_Prénom_1_scripts_mmaaaa` |
| 2 | **API de prédiction** (déployée sur le Cloud) | Flask/FastAPI | `Nom_Prénom_2_API_mmaaaa` |
| 3 | **Application web** (déployée sur le Cloud) | Streamlit/Flask | `Nom_Prénom_3_application_Flask_mmaaaa` |
| 4 | **Note technique** (~10 pages) | PDF | `Nom_Prénom_4_note_technique_mmaaaa` |
| 5 | **Présentation** (max 30 slides) | PPTX/PDF | `Nom_Prénom_5_presentation_mmaaaa` |
> Tout doit être dans un **zip** nommé `Titre_du_projet_nom_prénom`.
---
## Notions Clés à Maîtriser (Résumé)
| Domaine | Notions |
|---------|---------|
| **Computer Vision** | Semantic segmentation, encoder-decoder, skip connections, dilated convolutions |
| **Deep Learning** | Transfer learning, data augmentation, loss functions (Dice, Focal, CE), callbacks |
| **Keras/TensorFlow** | `tf.keras.utils.Sequence`, `keras.applications`, custom training loops, `MeanIoU` |
| **MLOps** | Docker, API REST, déploiement Cloud, CI/CD basique |
| **Data Engineering** | Data generators, label remapping, preprocessing pipelines |
| **Évaluation** | mIoU, Dice, pixel accuracy, confusion matrix, per-class metrics |
| **Communication** | Note technique, présentation de résultats, démo live |