Trigram (Trigramme)
Un trigram est une séquence de trois éléments consécutifs (mots ou caractères) extraits d’un texte. C’est un n-gram avec n=3. En NLP, les trigrams de mots comme « traitement du langage », « réseau de neurones » ou « taux de change » capturent un contexte plus large que les bigrams, permettant une meilleure modélisation du langage et une classification de texte plus fine.
Pour la phrase « Le traitement du langage naturel est fascinant », les trigrams sont : « Le traitement du », « traitement du langage », « du langage naturel », « langage naturel est », « naturel est fascinant ». Le trigram « traitement du langage » capture une expression composée de trois mots que ni les unigrams ni les bigrams ne peuvent représenter comme un concept unique.
- Catégorie
- N-gram avec n=3
- Synonyme
- Trigramme, 3-gram, triplet de mots
- Contexte capturé
- 2 mots précédents (hypothèse de Markov d’ordre 2)
- Usage principal
- Modèles de langage, classification de texte, détection de spam, détection de langue
- Librairies
- NLTK (trigrams, TrigramCollocationFinder), scikit-learn (ngram_range), Gensim
- Compromis
- Plus de contexte que le bigram, mais explosion du vocabulaire
Pourquoi les trigrams
Les bigrams capturent des paires de mots, mais beaucoup d’expressions porteuses de sens sont composées de trois mots. « Réseau de neurones », « intelligence artificielle générale », « taux de change », « machine à café », « pomme de terre » : ces concepts nécessitent trois mots pour être identifiés correctement. Avec des bigrams seuls, « réseau de » et « de neurones » sont deux features séparées qui perdent le lien entre « réseau » et « neurones ».
En modélisation du langage, le modèle trigramme représente un saut qualitatif par rapport au bigramme. En se basant sur les deux mots précédents plutôt qu’un seul, les phrases générées deviennent nettement plus cohérentes. Des expériences classiques décrites par Jurafsky et Martin montrent que les phrases générées par un modèle trigramme entraîné sur un corpus de Shakespeare commencent véritablement à ressembler à du Shakespeare, là où un modèle bigramme ne produit qu’une cohérence mot-à-mot superficielle.
Le trigram est souvent considéré comme le meilleur compromis entre contexte et faisabilité statistique. C’est le choix par défaut pour les modèles de langage classiques entraînés sur de grands corpus (millions de mots). Au-delà du trigram (4-gram, 5-gram), la parcimonie des données (data sparsity) devient si sévère que les gains sont marginaux.
Le modèle de langage trigramme
Un modèle de langage trigramme estime la probabilité d’un mot en fonction des deux mots précédents :
P(w3 | w1, w2) = count(w1, w2, w3) / count(w1, w2)
Pour la phrase « Le chat dort sur le canapé », le modèle calcule :
P("Le chat dort sur le canapé") ≈ P(Le|<s>,<s>) × P(chat|<s>,Le) × P(dort|Le,chat) × P(sur|chat,dort) × P(le|dort,sur) × P(canapé|sur,le) × P(</s>|le,canapé)
Chaque probabilité conditionnelle est estimée par maximum de vraisemblance (MLE) à partir des comptages observés dans le corpus d’entraînement. Le problème est que le nombre de trigrams possibles est colossal : avec un vocabulaire de 30 000 mots, il existe 27 × 10¹² trigrams possibles, dont l’immense majorité n’apparaîtra jamais dans aucun corpus réaliste.
Techniques de lissage
Pour éviter les probabilités nulles sur les trigrams non observés, plusieurs techniques de lissage sont utilisées :
L’interpolation linéaire combine les probabilités des unigrammes, bigrammes et trigrammes avec des poids λ appris sur un jeu de validation :
P_interp(w3|w1,w2) = λ1 × P(w3) + λ2 × P(w3|w2) + λ3 × P(w3|w1,w2)
Si le trigram n’est pas observé (λ3 × P = 0), l’interpolation retombe sur le bigram puis l’unigram, garantissant une probabilité non nulle. Le backoff (recul) est une variante qui utilise le trigram quand il est disponible, puis recule vers le bigram, puis l’unigram. Le lissage de Kneser-Ney, considéré comme le plus performant pour les modèles n-gram, combine le backoff avec une distribution de continuation qui favorise les mots apparaissant dans des contextes variés.
Implémentation en Python
Extraction de trigrams avec NLTK
import nltk
from nltk import trigrams
from nltk.tokenize import word_tokenize
phrase = "Le deep learning révolutionne la vision par ordinateur"
tokens = word_tokenize(phrase, language='french')
# Générer les trigrams
tri = list(trigrams(tokens))
for t in tri:
print(t)
# ('Le', 'deep', 'learning')
# ('deep', 'learning', 'révolutionne')
# ('learning', 'révolutionne', 'la')
# ('révolutionne', 'la', 'vision')
# ('la', 'vision', 'par')
# ('vision', 'par', 'ordinateur')
Construire un modèle trigramme avec NLTK
Voici un modèle de langage trigramme complet qui prédit le mot suivant à partir des deux mots précédents :
import nltk
from nltk import trigrams
from nltk.corpus import reuters
from collections import defaultdict
# Tokeniser le corpus Reuters
nltk.download('reuters')
nltk.download('punkt')
words = nltk.word_tokenize(' '.join(reuters.words()))
# Compter les trigrams
tri_grams = list(trigrams(words))
model = defaultdict(lambda: defaultdict(lambda: 0))
for w1, w2, w3 in tri_grams:
model[(w1, w2)][w3] += 1
# Convertir les comptages en probabilités
for w1_w2 in model:
total = float(sum(model[w1_w2].values()))
for w3 in model[w1_w2]:
model[w1_w2][w3] /= total
# Prédire le mot suivant
def predict_next(w1, w2):
probs = model.get((w1, w2), {})
if probs:
return max(probs, key=probs.get)
return "Pas de prédiction"
print(predict_next('the', 'stock')) # 'market' ou 'exchange'
print(predict_next('interest', 'rate')) # probablement un terme financier
Ce modèle est rudimentaire (pas de lissage, pas de gestion des mots inconnus), mais il illustre le principe fondamental des modèles de langage trigrammes : prédire le mot suivant à partir du contexte local des deux mots précédents.
Trigrams comme features avec scikit-learn
from sklearn.feature_extraction.text import TfidfVectorizer
corpus = [
"Le réseau de neurones convolutif excelle en vision",
"Le traitement du langage naturel utilise des transformers",
"Le réseau de neurones récurrent modélise les séquences"
]
# Unigrams + bigrams + trigrams
vectorizer = TfidfVectorizer(ngram_range=(1, 3))
X = vectorizer.fit_transform(corpus)
# Voir les features trigrams
features = vectorizer.get_feature_names_out()
trigram_features = [f for f in features if f.count(' ') == 2]
print("Trigrams détectés :", trigram_features[:10])
# ['de neurones convolutif', 'de neurones récurrent', 'du langage naturel',
# 'excelle en vision', 'le réseau de', 'le traitement du',
# 'modélise les séquences', 'naturel utilise des', 'neurones convolutif excelle',
# 'neurones récurrent modélise', ...]
print(f"Total features : {X.shape[1]}")
# Beaucoup plus que avec bigrams seuls
max_features pour limiter la taille, min_df=3 ou plus pour éliminer les trigrams rares, et évaluez si le gain en précision justifie le surcoût en dimensionnalité par rapport aux bigrams seuls.
Cas d’usage
Détection de spam
Les trigrams sont particulièrement efficaces pour la détection de spam. Des études montrent que des modèles combinant SVM avec des features trigrams atteignent environ 89 % de précision pour l’identification de spam dans les avis en ligne. Les trigrams capturent des expressions typiques du spam comme « offre limitée durée », « gagnez un voyage » ou « cliquez ici maintenant » qui échappent aux bigrams.
Détection de langue
Les trigrams de caractères sont la méthode standard pour la détection automatique de langue. Chaque langue a une distribution unique de trigrams de caractères. Par exemple, « sch » est typique de l’allemand, « ght » de l’anglais, « tion » du français. En comparant la distribution des trigrams de caractères d’un texte inconnu avec des profils de référence pour chaque langue, on peut identifier la langue avec une précision supérieure à 99 % pour les textes de plus de quelques dizaines de mots.
Correction orthographique et détection de gibberish
Un modèle trigramme de caractères entraîné sur un corpus propre attribue une probabilité faible aux séquences de caractères inhabituelles. Si un mot contient le trigram « xzq », sa probabilité sera très basse, signalant une faute d’orthographe ou du texte généré automatiquement (gibberish). Cette technique est utilisée pour filtrer les données d’entraînement des LLM et pour détecter les contenus spam ou générés.
Classification de texte améliorée
L’ajout de trigrams aux features TF-IDF peut améliorer la classification quand le corpus contient des expressions à trois mots discriminantes. C’est le cas dans les domaines techniques (« réseau de neurones », « apprentissage par renforcement »), juridiques (« cour de cassation », « tribunal de commerce ») et médicaux (« insuffisance rénale chronique », « trouble du spectre »). Pour les corpus généralistes, le gain des trigrams par rapport aux bigrams est souvent marginal.
Évaluation des modèles de génération
La métrique BLEU, standard pour évaluer la traduction automatique et la génération de texte, repose sur la comparaison de n-grams entre le texte généré et la référence. BLEU-3 mesure spécifiquement la proportion de trigrams du texte généré qui se retrouvent dans la référence. Un score BLEU-3 élevé indique que le texte généré reproduit fidèlement les enchaînements de trois mots de la référence.
Trigram vs bigram : quand monter en ordre
| Critère | Bigram (n=2) | Trigram (n=3) |
|---|---|---|
| Contexte capturé | 1 mot précédent | 2 mots précédents |
| Taille vocabulaire | V² (modérée) | V³ (explosive) |
| Data sparsity | Modérée | Sévère |
| Cohérence des phrases générées | Locale, mot-à-mot | Nettement meilleure |
| Gain en classification | Souvent significatif vs unigrams | Parfois marginal vs bigrams |
| Corpus minimum recommandé | Centaines de milliers de mots | Millions de mots |
| Usage recommandé | Choix par défaut pour features | Domaines spécialisés, modèles de langage |
En pratique pour la classification de texte, commencez toujours par unigrams + bigrams (ngram_range=(1,2)). N’ajoutez les trigrams (ngram_range=(1,3)) que si vous avez un corpus suffisamment grand (plusieurs dizaines de milliers de documents) ET que votre domaine contient beaucoup d’expressions à trois mots discriminantes. Mesurez systématiquement le gain en précision par rapport au surcoût en dimensionnalité et en temps de calcul.
Trigrams de caractères
Les trigrams de caractères découpent les mots en séquences de trois caractères consécutifs. Pour « bonjour », les trigrams sont : « bon », « onj », « njo », « jou », « our ». Cette approche a des applications distinctes des trigrams de mots.
La détection de langue est le cas d’usage le plus performant. Le trigram de caractères « the » est caractéristique de l’anglais, « sch » de l’allemand, « ção » du portugais, « ent » du français. Des librairies comme langdetect ou fasttext utilisent ce principe pour identifier la langue d’un texte en quelques millisecondes.
La détection de spam par modèle trigramme de caractères est décrite en détail dans la littérature. Le principe est simple : entraîner un modèle sur du texte lisible, puis calculer la log-probabilité de nouvelles chaînes. Une chaîne comme « xkjdq » aura une probabilité extrêmement faible (les trigrams « xkj », « kjd », « jdq » sont quasi inexistants en langue naturelle), ce qui la signale comme spam ou gibberish.
scikit-learn supporte les trigrams de caractères via TfidfVectorizer(analyzer='char', ngram_range=(3,3)) ou analyzer='char_wb' (qui respecte les frontières de mots).
Au-delà des trigrams : pourquoi les transformers ont gagné
Le modèle trigramme, aussi perfectionné soit-il avec le lissage de Kneser-Ney, souffre d’une limitation fondamentale : il ne voit que deux mots en arrière. Les dépendances à longue distance (un sujet en début de phrase accordé avec un verbe en fin de phrase) lui sont invisibles.
Les transformers et les LLM modernes n’ont pas cette limitation. Leur mécanisme d’attention considère l’intégralité de la séquence d’entrée (fenêtres de contexte de 128 000 tokens et plus), ce qui leur permet de capturer des relations à n’importe quelle distance. C’est la raison principale pour laquelle les modèles de langage n-gram ont été remplacés par les architectures neuronales pour la génération de texte, la traduction et toutes les tâches nécessitant une compréhension globale du contexte.
Cependant, les concepts théoriques des modèles trigrammes (probabilités conditionnelles, perplexité, lissage, interpolation) restent au fondement de la théorie des modèles de langage. Comprendre les trigrams, c’est comprendre les bases sur lesquelles les LLM ont été construits.
Bonnes pratiques en production
Si vous utilisez des trigrams comme features TF-IDF, appliquez systématiquement un filtre min_df=3 ou supérieur. Un trigram qui n’apparaît que dans un ou deux documents est du bruit statistique qui gonfle le vocabulaire sans améliorer la classification. Combinez ce filtre avec max_features=20000 ou 50000 pour plafonner la dimensionnalité.
Prétraitez le texte avant de générer les trigrams. Le stemming ou la lemmatisation permettent de regrouper les variantes morphologiques : « réseaux de neurones » et « réseau de neurone » convergent vers le même trigram après lemmatisation. La suppression des stopwords élimine les trigrams non informatifs comme « dans le cas » ou « il est de ».
Pour les trigrams de caractères, le paramètre analyzer='char_wb' de scikit-learn est préférable à analyzer='char' : il ne traverse pas les frontières de mots, évitant de créer des trigrams artificiels à la jonction de deux mots. Combinez les trigrams de caractères (pour la robustesse aux fautes) avec les trigrams de mots (pour le contexte sémantique) dans un pipeline de classification pour de meilleurs résultats.
Qu’est-ce qu’un trigram en NLP ?
Un trigram est une séquence de trois éléments consécutifs (mots ou caractères) extraits d’un texte. C’est un n-gram avec n=3. Exemples : « traitement du langage », « réseau de neurones », « taux de change ». Les trigrams capturent un contexte plus large que les bigrams (deux mots), permettant une meilleure modélisation du langage et une classification de texte plus précise pour les expressions à trois mots.
Quand utiliser des trigrams plutôt que des bigrams ?
Utilisez des trigrams quand votre domaine contient beaucoup d’expressions à trois mots discriminantes (terminologie technique, juridique, médicale), quand vous construisez un modèle de langage probabiliste sur un corpus de millions de mots, ou quand vous faites de la détection de langue avec des trigrams de caractères. Pour la classification de texte standard, les bigrams suffisent souvent. Testez toujours les deux configurations sur vos données et comparez les métriques.
Comment implémenter les trigrams en Python ?
Avec NLTK : from nltk import trigrams, puis tri = list(trigrams(tokens)). Avec scikit-learn pour la classification : TfidfVectorizer(ngram_range=(1, 3)) génère automatiquement les unigrams, bigrams ET trigrams comme features TF-IDF. Pour un modèle de langage trigramme, utilisez NLTK avec des comptages de trigrams convertis en probabilités conditionnelles, idéalement avec un lissage (interpolation linéaire ou Kneser-Ney).
Les trigrams sont-ils encore utilisés avec les LLM ?
Les modèles de langage trigrammes ont été remplacés par les transformers pour la génération de texte. Cependant, les trigrams restent utilisés comme features pour la classification de texte (TF-IDF avec ngram_range=(1,3)), pour la détection de langue (trigrams de caractères), pour l’évaluation des LLM (métrique BLEU-3), et dans les systèmes embarqués à faibles ressources. Les concepts théoriques des trigrams (probabilités conditionnelles, perplexité) sont toujours enseignés car ils fondent la théorie des modèles de langage.
Quel est le problème principal des trigrams ?
La parcimonie des données (data sparsity). Avec un vocabulaire de 30 000 mots, il existe 27 × 10¹² trigrams possibles. La quasi-totalité n’apparaîtra jamais dans votre corpus d’entraînement. Les trigrams non observés reçoivent une probabilité de zéro (sans lissage), ce qui empêche le modèle de traiter correctement les phrases contenant des enchaînements nouveaux. Les techniques de lissage (interpolation, backoff, Kneser-Ney) atténuent le problème mais ne le résolvent pas fondamentalement.