Une règle d’association à 90 % de confiance peut être moins informative qu’une règle à 80 %. Tout dépend de la fréquence habituelle du produit recommandé. Si B apparaît déjà dans 95 % des paniers, le retrouver dans 90 % des paniers contenant A n’est pas un gain par rapport à cette référence.
Ce cas pratique complète le guide FP-Growth par un contre-exemple calculable à la main et reproductible en Python. Les cent paniers sont entièrement fabriqués pour expliquer les métriques : ils ne décrivent aucune boutique.
Cent paniers, quatre produits, deux règles
| Effectif | Nombre de paniers |
|---|---|
| A présent | 10 |
| B présent | 95 |
| A et B présents | 9 |
| C présent | 10 |
| D présent | 10 |
| C et D présents | 8 |
Le CSV contient une ligne par panier, un identifiant et quatre colonnes booléennes. Un panier peut contenir plusieurs produits. Les lignes sans ces quatre produits sont conservées : elles représentent des paniers sans article de notre petit catalogue, et comptent dans le dénominateur de cent transactions.
Support, confiance, lift : faire les divisions
Le support de A→B correspond à la proportion de paniers contenant A et B : 9 / 100 = 0,09. La confiance conditionne sur A : 9 / 10 = 0,90. Le lift divise cette confiance par le support de B : 0,90 / 0,95 ≈ 0,9474. Ces définitions suivent la documentation des règles d’association de mlxtend.
| Règle | Support conjoint | Confiance | Fréquence du conséquent | Lift |
|---|---|---|---|---|
| A→B | 9 % | 90 % | B : 95 % | 0,9474 |
| C→D | 8 % | 80 % | D : 10 % | 8,0000 |
Avec A→B, le conséquent est légèrement moins fréquent en présence de l’antécédent que dans l’ensemble des paniers. Avec C→D, il est huit fois plus fréquent. Le classement par confiance privilégierait pourtant A→B. Le problème ne vient pas de FP-Growth : il vient de l’interprétation du critère choisi.

Ce que fait FP-Growth dans cet exemple
fpgrowth extrait les ensembles fréquents à partir des colonnes booléennes. Nous fixons un support minimal de 5 % et une taille maximale de deux produits pour garder une démonstration lisible. association_rules construit ensuite les règles dont la confiance atteint 80 %. Cinq règles passent ce filtre ; nous examinons deux règles définies dans le scénario. Consultez la référence de fpgrowth pour les paramètres.
Monter le support minimal à 9 % élimine C→D, dont le support conjoint n’est que de 8 %. Ce filtre peut être utile pour éviter des effectifs trop petits ; il peut aussi retirer une association intéressante pour un segment rare. Le seuil doit correspondre au problème et aux données disponibles.
Reproduire le calcul en Python
Télécharger les paniers CSV, le script et les quatre tests — ZIP gratuit. Exemple exécuté le 20 octobre 2026 avec Python 3.12.14 et mlxtend 0.25.0. Les versions directes sont fixées dans requirements.txt. Lancez python regles_paniers.py, puis python test_exemple.py.
"""100 paniers artificiels : une confiance élevée peut cacher un lift inférieur à 1."""
import json
from pathlib import Path
import pandas as pd
import matplotlib
matplotlib.use("Agg")
import matplotlib.pyplot as plt
from mlxtend.frequent_patterns import fpgrowth, association_rules
OUT = Path(__file__).resolve().parent
def paniers():
presences = {
"A": set(range(10)),
"B": set(range(9)) | set(range(10, 96)),
"C": set(range(40, 50)),
"D": set(range(40, 48)) | {96, 97},
}
return pd.DataFrame({nom: [i in ids for i in range(100)]
for nom, ids in presences.items()}, dtype=bool)
def regles(df, support=.05):
frequents = fpgrowth(df, min_support=support, use_colnames=True, max_len=2)
return association_rules(frequents, num_itemsets=len(df),
metric="confidence", min_threshold=.8)
def extraire(rules, a, b):
ligne = rules[(rules["antecedents"] == frozenset([a])) &
(rules["consequents"] == frozenset([b]))].iloc[0]
return {"regle": a + " -> " + b,
**{k: float(ligne[k]) for k in ["support", "confidence", "lift", "consequent support"]}}
def experience():
df = paniers()
df.to_csv(OUT / "paniers_synthetiques.csv", index_label="panier_id")
rules = regles(df)
retenues = [extraire(rules, "A", "B"), extraire(rules, "C", "D")]
pd.DataFrame(retenues).to_csv(OUT / "deux_regles.csv", index=False)
fig, ax = plt.subplots(figsize=(9, 4.8), layout="constrained")
x = [0, 1]
ax.bar([v-.18 for v in x], [r["confidence"] for r in retenues], .36,
label="Confiance P(conséquent | antécédent)", color="#167c80")
ax.bar([v+.18 for v in x], [r["consequent support"] for r in retenues], .36,
label="Fréquence du conséquent dans tous les paniers", color="#e0a13b")
ax.set(xticks=x, xticklabels=["A → B : lift ≈ 0,95", "C → D : lift = 8"],
ylim=(0, 1.23), ylabel="Proportion", title="Une confiance de 90 % peut être moins informative que 80 %")
ax.legend(loc="upper center", fontsize=9)
fig.savefig(OUT / "figure.png", dpi=160)
plt.close(fig)
return {"paniers": len(df), "effectifs": {c: int(df[c].sum()) for c in df},
"regles": retenues, "regles_generees": len(rules)}
if __name__ == "__main__":
resultats = experience()
(OUT / "resultats.json").write_text(json.dumps(resultats, indent=2), encoding="utf-8")
print(json.dumps(resultats, indent=2))
Un lift élevé ne suffit toujours pas à recommander
Dans notre deuxième règle, dix paniers seulement contiennent C. Huit cooccurrences construites pour une démonstration ne suffisent pas à valider une politique de recommandation. Un lift de huit ne signifie pas que montrer D multipliera les ventes par huit : l’association observée ne mesure pas l’effet d’une intervention.
Avant de retenir une règle dans un vrai projet, examinez ses effectifs, sa stabilité sur une période ultérieure et sa pertinence métier. Une promotion commune, une catégorie de clients ou une contrainte de stock peuvent expliquer une cooccurrence. Les règles choisies après exploration de centaines de combinaisons demandent aussi une validation sur des données séparées.
Pour préparer cette validation, gardez la période récente à l’écart, calculez les règles sur la période ancienne et évaluez les mêmes règles sur la période récente. Ne changez pas simultanément la définition d’un panier, les produits inclus et le seuil : vous ne sauriez plus expliquer l’écart.
Un exercice pour prolonger le cas
Modifiez seulement les paniers contenant B : faites passer sa fréquence globale de 95 % à 90 %, en conservant neuf cooccurrences avec A et dix paniers A. Avant d’exécuter, prévoyez le lift. Il doit devenir exactement un. Puis expliquez pourquoi une confiance de 90 % reste insuffisante pour conclure à une association positive.
Pour travailler les fichiers d’entrée, utilisez les cinq exercices CSV corrigés. Le catalogue de cas pratiques propose d’autres exemples où un score isolé peut tromper.

