Guide Pratique : Régression Linéaire sur le Dataset Advertising

8 min de lecture

📚 Introduction

Ce guide vous accompagne pas à pas dans l'analyse du dataset Advertising pour prédire les ventes en fonction des budgets publicitaires (TV, radio, journaux).

Télécharger le fichier CSV

Objectif : Comprendre comment construire un modèle de régression linéaire, l'évaluer, et l'améliorer avec des techniques simples.


Comprendre les données

Le dataset Advertising

200 observations avec 4 variables :

Variable Description Type
tv Budget pub TV (milliers €) Variable prédictive
radio Budget pub radio (milliers €) Variable prédictive
journaux Budget pub journaux (milliers €) Variable prédictive
ventes Volume de ventes Variable cible (ce qu'on veut prédire)

Première exploration

import pandas as pd

df = pd.read_csv("advertising.csv")
print(df.head())
print(df.describe())

Ce qu'on observe :

  • Moyenne TV : ~147, Radio : ~23, Journaux : ~31
  • Ventes moyennes : ~14
  • Aucune valeur manquante ✅

Visualiser les relations

Pourquoi visualiser ?

Avant de construire un modèle, il faut voir si les variables sont liées aux ventes.

Les graphiques avec trendline (ligne de régression)

import plotly.express as px

fig = px.scatter(df, x="tv", y="ventes",
                 trendline="ols",  # Ordinary Least Squares
                 title="TV vs Ventes")
fig.show()

Ce que montre le paramètre trendline="ols" :

  • Trace automatiquement la meilleure droite qui passe au plus près des points
  • OLS = méthode mathématique pour trouver cette droite
  • Si les points sont proches de la ligne → forte relation 💪
  • Si les points sont dispersés → faible relation 😐

Les corrélations

Variables Corrélation avec ventes
tv 0.78 🔥 (très forte)
radio 0.58 👍 (forte)
journaux 0.23 😐 (faible)

Interprétation simple :

  • 0.78 : Quand le budget TV augmente, les ventes augmentent beaucoup
  • 0.23 : Les journaux ont peu d'impact sur les ventes

Construire le modèle de régression linéaire

Qu'est-ce qu'une régression linéaire ?

C'est trouver la formule mathématique qui relie les variables :

ventes = a × tv + b × radio + c × journaux + d

Le modèle va chercher les meilleurs coefficients a, b, c, d pour prédire au mieux les ventes.

Le code

from sklearn.linear_model import LinearRegression
from sklearn.model_selection import train_test_split

# 1. Préparer les données
X = df[["tv", "radio", "journaux"]]  # Variables prédictives
y = df.ventes                        # Variable cible

# 2. Séparer en train (80%) et test (20%)
X_train, X_test, y_train, y_test = train_test_split(
    X, y, test_size=0.20, random_state=42
)

# 3. Créer et entraîner le modèle
reg = LinearRegression()
reg.fit(X_train, y_train)  # Le modèle "apprend"

# 4. Faire des prédictions
y_pred_test = reg.predict(X_test)

🧠 Comprendre train_test_split

Pourquoi séparer les données ?

Imaginez que vous préparez un examen :

  • Train (80%) = Les exercices que vous faites pour apprendre
  • Test (20%) = L'examen final avec des questions que vous n'avez jamais vues

Si vous testez sur les mêmes données que l'entraînement, vous trichez ! Le modèle connaît déjà les réponses.

Le paramètre random_state=42 :

  • Assure que la séparation est toujours la même
  • Permet de reproduire les résultats
  • Sans ça, chaque exécution donnerait des résultats différents

Évaluer le modèle

Les métriques d'évaluation

from sklearn.metrics import mean_squared_error, mean_absolute_percentage_error

rmse = mean_squared_error(y_test, y_pred_test)
mape = mean_absolute_percentage_error(y_test, y_pred_test)

print(f"RMSE : {rmse}")
print(f"MAPE : {mape}")

📏 RMSE (Root Mean Square Error)

C'est quoi ? L'erreur moyenne de vos prédictions.

Exemple concret :

  • Si RMSE = 3.17
  • En moyenne, vos prédictions se trompent de ±3.17 unités de ventes
  • Si les vraies ventes sont 15, vous prédisez entre 11.83 et 18.17

Caractéristique : Pénalise fortement les grosses erreurs

  • Se tromper de 10 compte plus que se tromper de 1 dix fois

🎯 MAPE (Mean Absolute Percentage Error)

C'est quoi ? L'erreur en pourcentage.

Exemple concret :

  • Si MAPE = 0.15 (soit 15%)
  • En moyenne, vos prédictions ont 15% d'erreur
  • Si les vraies ventes sont 100, vous prédisez entre 85 et 115

Avantage : Plus intuitif et comparable entre différents projets

Est-ce bon ou mauvais ?

Pour le modèle simple :

  • RMSE ≈ 3.17 → Pas mal 👍
  • MAPE ≈ 0.15 (15%) → Correct mais peut mieux faire 🤔

Amélioration : La régression polynomiale

Le problème détecté

En regardant le graphique TV vs Ventes, on remarque que les points forment une courbe plutôt qu'une ligne droite.

Exemple visuel :

Budget TV faible (0-50)    → Les ventes augmentent lentement
Budget TV moyen (100-150)  → Les ventes augmentent normalement
Budget TV élevé (200-300)  → Les ventes augmentent rapidement

C'est une accélération = relation non-linéaire !

La solution : ajouter tv²

Au lieu de :

ventes = a × tv + ...

On fait :

ventes = a × tv + b × tv² + ...

Pourquoi tv² capture la courbure ?

Exemple simple :

tv tv² Rapport
10 100 -
20 400 ×4 (pas ×2 !)
30 900 ×9 (pas ×3 !)

Le terme tv² augmente beaucoup plus vite que tv, ce qui crée l'effet de courbure/accélération.


Normalisation : Pourquoi et comment ?

Le problème d'échelle

Après avoir créé tv², on a :

  • tv : entre 0 et 300
  • tv² : entre 0 et 90 000 ! 😱

Le modèle va penser que tv² est beaucoup plus important juste parce que les chiffres sont gros.

La solution : MinMaxScaler

Ce que ça fait : Ramène toutes les variables entre 0 et 1.

Exemple :

Avant :
tv = [0, 100, 200, 300]

Après normalisation :
tv = [0, 0.33, 0.66, 1.0]

Le code

from sklearn.preprocessing import MinMaxScaler

# 1. Créer tv²
df['tv2'] = df.tv ** 2

# 2. Normaliser
scaler = MinMaxScaler()
data_normalized = scaler.fit_transform(df)
df_normalized = pd.DataFrame(data_normalized,
                              columns=['tv', 'radio', 'journaux', 'ventes', 'tv2'])

# 3. Entraîner avec tv²
X_poly = df_normalized[['tv', 'radio', 'journaux', 'tv2']]
y_poly = df_normalized.ventes

X_train, X_test, y_train, y_test = train_test_split(
    X_poly, y_poly, test_size=0.20, random_state=42
)

reg_poly = LinearRegression()
reg_poly.fit(X_train, y_train)
y_pred_poly = reg_poly.predict(X_test)

Comprendre fit_transform

Les 4 étapes du scaler :

  1. fit() : Le scaler regarde les données et calcule :

    • Le minimum de chaque colonne
    • Le maximum de chaque colonne
  2. transform() : Le scaler applique la formule :

    valeur_normalisée = (valeur - min) / (max - min)
    
  3. fit_transform() : Fait les 2 étapes d'un coup (plus rapide)

Exemple concret :

tv = [0, 100, 200, 300]

# Le scaler calcule :
min = 0
max = 300

# Puis transforme :
0   → (0 - 0) / 300 = 0
100 → (100 - 0) / 300 = 0.33
200 → (200 - 0) / 300 = 0.66
300 → (300 - 0) / 300 = 1.0

Comparaison des résultats

Tableau récapitulatif

Modèle Variables utilisées RMSE MAPE Amélioration
Linéaire simple tv, radio, journaux ~3.17 ~0.15 -
Polynomiale tv, radio, journaux, tv² Plus petit Plus petit ✅ Meilleur

Pourquoi c'est mieux ?

Le terme quadratique tv² permet de capturer la vraie relation entre TV et ventes :

  • Pas juste une ligne droite
  • Mais une courbe qui représente l'accélération des ventes avec le budget

Convention de nommage importante

La notation _pred

En machine learning, on utilise cette convention :

Variable Signification
y_test Les vraies valeurs de ventes
y_pred_test Les valeurs prédites par le modèle

Pourquoi c'est important ?

  • Distingue clairement la réalité des prédictions
  • Évite les confusions dans le code
  • Standard dans toute la communauté ML

Analogie :

  • y_test = Les bonnes réponses de l'examen
  • y_pred_test = Vos réponses (ce que le modèle pense)
  • Les métriques (RMSE, MAPE) = La note de l'examen (comparaison des deux)

🎓 Concepts clés à retenir

1. Train/Test Split

Toujours séparer les données
✅ Typiquement 80/20 ou 70/30
✅ Le modèle n'a jamais vu les données de test

2. Corrélation

✅ Entre -1 et +1
✅ Plus proche de ±1 = plus forte relation
✅ Proche de 0 = pas de relation

3. Régression polynomiale

✅ Ajouter des puissances (x²) capture les courbes
✅ Plus flexible que la régression linéaire simple
✅ Attention à ne pas "sur-complexifier" (overfitting)

4. Normalisation

✅ Met toutes les variables sur la même échelle
✅ Permet de comparer l'importance des coefficients
✅ Évite que les grandes valeurs dominent

5. Métriques d'évaluation

RMSE : Erreur absolue, pénalise les grosses erreurs
MAPE : Erreur en %, facile à interpréter
✅ Plus petit = meilleur modèle


🚀 Pour aller plus loin

Idées d'améliorations

  1. Ajouter des termes croisés : tv × radio

    • Capture l'effet combiné de campagnes multi-canal
  2. Retirer la variable journaux

    • Corrélation faible (0.23), peut simplifier le modèle
  3. Tester d'autres modèles

    • Random Forest, Gradient Boosting
    • Comparer les performances
  4. Analyser les résidus

    • Différence entre prédiction et réalité
    • Identifier les patterns d'erreurs

📝 Résumé du workflow complet

1. Charger les données
   ↓
2. Explorer (head, describe, visualisations)
   ↓
3. Analyser les corrélations
   ↓
4. Préparer X (variables) et y (cible)
   ↓
5. Split train/test
   ↓
6. Entraîner le modèle (fit)
   ↓
7. Prédire (predict)
   ↓
8. Évaluer (RMSE, MAPE)
   ↓
9. Améliorer (ajouter tv², normaliser)
   ↓
10. Comparer les résultats

💡 Analogies pour bien comprendre

Le modèle = Un étudiant

  • fit() = Réviser avec les exercices du livre
  • predict() = Passer l'examen
  • Train set = Les exercices du livre
  • Test set = L'examen avec de nouvelles questions
  • RMSE/MAPE = La note de l'examen

La régression linéaire = Tracer une droite

  • On a des points sur un graphique
  • On cherche la meilleure droite qui passe près de tous les points
  • Les coefficients = La pente et la hauteur de la droite
  • L'erreur = La distance moyenne entre les points et la droite

La normalisation = Mettre tout en euros

  • Sans normalisation : comparer des pommes (2€) et des voitures (20 000€)
  • Avec normalisation : tout entre 0 et 1, on compare des proportions
  • Comme mettre toutes les valeurs en "pourcentage du maximum"
Clément R
~
Partager :