Aller au contenu principal

Module 1 — Formuler un problème de recommandation

Avant tout code, il faut décider ce que le système doit produire. Ce module cadre le problème pour éviter l'erreur qui coûte le plus cher en pratique : entraîner un excellent régresseur de notes qui ne recommande rien de bon.

Prédire une note, ou ordonner un catalogue ?

Le concours Netflix a durablement installé une confusion. Sa consigne était de prédire, pour un couple (utilisateur, film), la note explicite à 0,01 étoile près, mesurée par l'erreur quadratique moyenne (RMSE). Toute la littérature qui en est issue a suivi ce cadrage, alors que la question métier réelle est ailleurs.

En production, un moteur de recommandation ne montre jamais une note prédite. Il choisit, parmi 500 cours du catalogue InSkillML, les cinq ou dix à mettre en avant sur la page d'accueil de chaque apprenant. C'est un problème de classement top-k, pas de régression. Deux modèles peuvent afficher exactement la même RMSE en produisant des classements très différents : l'un place systématiquement les cours pertinents dans les cinq premiers, l'autre les enfouit en position 40. Le premier fait vendre, le second est inutile.

Cette différence n'est pas un détail. La RMSE punit à parts égales une erreur de 0,5 étoile sur un cours que personne ne verra et une erreur qui fait sortir un cours pertinent du top-10. Or seule la seconde erreur a un impact métier. La bonne métrique regarde uniquement les k premières positions : rappel@k, précision@k, NDCG@k, MAP@k. Nous les définirons rigoureusement au module 8 ; retenez pour l'instant qu'une amélioration de 0,03 sur la RMSE ne dit rien sur la qualité perçue par l'apprenant.

Rétroaction explicite et implicite

La donnée d'entrée d'un système de recommandation prend deux formes très différentes, et la formulation change avec elle.

La rétroaction explicite est un jugement conscient : une note d'un à cinq, un pouce levé, un signalement « inutile ». Elle est rare — moins de 5 % des apprenants notent un cours qu'ils ont pourtant terminé — et elle est biaisée. Ceux qui prennent le temps de noter sont soit ravis, soit furieux ; les indifférents se taisent. La distribution en U typique de MovieLens et de nos cours en atteste : peu de trois étoiles, beaucoup de cinq et une queue de un.

La rétroaction implicite est un comportement observé : inscription à un cours, minutes visionnées, achèvement, ajout aux favoris, achat du certificat. Elle est abondante — chaque clic est enregistré — mais ambiguë. Un apprenant qui n'a pas cliqué sur un cours ne l'a peut-être pas trouvé mauvais : il ne l'a jamais vu s'afficher. C'est la différence essentielle avec l'explicite. Dans une note, l'absence signifie ignorance ; dans un clic, l'absence peut signifier rejet ou non-exposition. Le module 9 formalisera cet asymétrie et introduira la pondération par confiance qui la corrige.

En pratique, les systèmes modernes reposent d'abord sur l'implicite parce qu'il couvre tout le monde ; l'explicite ne sert qu'à raffiner les signaux ambigus. C'est un renversement complet par rapport aux années Netflix.

La matrice utilisateur-objet et son creux extrême

Représentons les données comme une matrice RR de UU lignes (utilisateurs) et II colonnes (cours). L'entrée Ru,iR_{u,i} est la note explicite, le nombre de minutes visionnées, ou zéro si l'interaction n'a pas eu lieu.

Cette matrice est presque vide. Sur InSkillML, avec 30 000 apprenants et 500 cours, la matrice compte 15 millions de cellules. Un apprenant suit en moyenne cinq cours ; l'ensemble des interactions représente donc 150 000 cellules non nulles, soit 1 % de la matrice. Sur MovieLens 25M, la densité est de 1,3 %. À l'échelle d'Amazon ou de Netflix, elle descend sous 0,1 %.

Cette rareté conditionne tout ce qui suit. Elle explique pourquoi le filtrage collaboratif par voisinage souffre dès qu'un utilisateur a peu d'interactions (module 2), pourquoi la factorisation matricielle a besoin de régularisation (module 3), et pourquoi le démarrage à froid — un utilisateur ou un cours sans historique — est un problème séparé qui exige des signaux extérieurs à la matrice (module 7).

Le format de stockage compte aussi. Une matrice dense de 15 millions de flottants pèse 120 Mo ; un format creux (scipy.sparse.csr_matrix) qui ne stocke que les cellules non nulles pèse moins de 2 Mo. Toutes les bibliothèques sérieuses (implicit, Surprise, LightFM) opèrent en creux.

import numpy as np
import pandas as pd
from scipy.sparse import csr_matrix

# Journal d'interactions : une ligne par (apprenant, cours, note).
inter = pd.DataFrame({
"apprenant": [1, 1, 2, 3, 3, 4],
"cours": [10, 20, 20, 30, 10, 40],
"note": [5, 4, 3, 5, 4, 2],
})

# Encodage compact des identifiants pour indexer la matrice.
u_ids = {u: i for i, u in enumerate(inter["apprenant"].unique())}
i_ids = {c: i for i, c in enumerate(inter["cours"].unique())}
lignes = inter["apprenant"].map(u_ids).to_numpy()
cols = inter["cours"].map(i_ids).to_numpy()

R = csr_matrix((inter["note"], (lignes, cols)),
shape=(len(u_ids), len(i_ids)))

densite = R.nnz / (R.shape[0] * R.shape[1])
print(f"densité de la matrice : {densite:.2%}")

L'objectif métier réel

Une recommandation utile se juge en aval, pas sur la métrique de tri hors ligne. Sur une plateforme de cours, trois objectifs coexistent et se contredisent parfois : maximiser les inscriptions, faire progresser le taux d'achèvement, et maintenir la diversité du parcours d'apprentissage. Recommander cinq cours de Python à quelqu'un qui vient de finir « Introduction à Python » maximise probablement le taux de clic à court terme mais bloque la progression et lasse l'apprenant.

Cet arbitrage se traduit dans la métrique optimisée. Le module 8 introduira les métriques de couverture du catalogue et de diversité intra-liste précisément pour éviter ce piège. Pour l'instant, retenez qu'une équipe qui ne pose pas cette question dès la formulation construit un moteur qui améliore ses métriques et dégrade son produit.

Le piège de la RMSE

Reproduire le concours Netflix en 2026 est un contresens. Si votre validation compare des modèles par RMSE ou MAE et que le comité de projet félicite l'équipe pour un gain de deux décimales, il y a une forte probabilité que ces deux décimales soient invisibles en A/B test. Le module 8 explique pourquoi ; le module 10 le mesure sur les données du fil rouge.

En résumé

  • Un système de recommandation classe un catalogue, il ne prédit pas une note ; la RMSE ne mesure donc pas la qualité perçue.
  • La rétroaction explicite est rare et biaisée ; la rétroaction implicite est abondante mais ambiguë — l'absence d'un clic n'est pas un rejet.
  • La matrice utilisateur-objet est extrêmement creuse (souvent moins de 1 %) et doit être stockée en format sparse.
  • L'objectif métier réel est un arbitrage entre inscriptions, achèvement et diversité ; le fixer dès la formulation évite d'optimiser une métrique déconnectée du produit.

Module suivant : le filtrage collaboratif par voisinage, la méthode la plus ancienne et toujours la plus lisible.