title | description | prev | next | type | id |
---|---|---|---|---|---|
Chapitre 4 : Entrainement d'un modèle de réseau de neurones |
Dans ce chapitre, tu vas apprendre comment actualiser les modèles statistiques de spaCy afin de les personnaliser pour tes cas d'utilisation - par exemple, pour prédire un nouveau type d'entité pour des commentaires en ligne. Tu vas écrire ta propre boucle d'apprentissage en partant de zéro, et comprendre les bases de l'apprentissage, ainsi que des trucs et astuces pour mieux réussir tes projets de NLP sur mesure. |
/chapter3 |
chapter |
4 |
Bien que spaCy comporte une série de modèles pré-entrainés pour prédire des annotations linguistiques, tu voudras presque toujours le perfectionner avec plus d'exemples. Tu peux le faire en les entrainant avec davantage de données étiquetées.
Qu'est-ce que l'apprentissage n'améliore pas ?
Si un modèle pré-entrainé ne donne pas de bons résultats sur tes données, l'entrainer avec davantage d'exemples est souvent une bonne solution.
Tu peux utiliser l'apprentissage pour apprendre au modèle de nouveaux labels, de nouveaux types d'entités ou d'autres schémas de classification.
Les composants de spaCy sont des modèles supervisés pour l'annotation de texte, ce qui signifie qu'ils peuvent seulement apprendre à reproduire des exemples, mais pas deviner de nouveaux labels à partir de texte brut.
Le Matcher
basé sur les règles de spaCy est un excellent moyen pour créer
rapidement des données d'apprentissage pour les modèles d'entités nommées. Une
liste de phrases est accessible via la variable TEXTS
. Tu peux l'imprimer pour
l'inspecter. Nous voulons trouver toutes les mentions de différents modèles
d'iPhone, donc nous allons créer des données d'entrainement pour apprendre à
notre modèle à les reconnaitre en tant que "GADGET"
.
- Écris un motif pour deux tokens dont la forme en minuscules correspond à
"iphone"
et"x"
. - Écris un motif pour deux tokens : un token dont la forme en minuscules
correspond à
"iphone"
et un chiffre.
- Pour trouver les formes minuscules d'un token, tu peux utiliser l'attribut
"LOWER"
. Par exemple :{"LOWER": "apple"}
. - Pour trouver un token numérique, tu peux utiliser le marqueur
"IS_DIGIT"
. Par exemple :{"IS_DIGIT": True}
.
Utilisons les motifs de correspondance que nous avons créé dans l'exercice
précédent pour améliorer un ensemble d'exemples d'apprentissage. Une liste de
phrases est accessible via la variable TEXTS
.
- Crée un objet doc pour chaque texte en utilisant
nlp.pipe
. - Trouve les correspondances sur le
doc
et crée une liste des spans qui correspondent. - Obtiens les tuples
(start character, end character, label)
des spans qui correspondent. - Formate chaque exemple en tuple avec le texte et un dictionnaire qui fait
correspondre la clé
"entities"
aux tuples d'entités. - Ajoute l'exemple au
TRAINING_DATA
et inspecte les données affichées.
- Pour trouver les correspondances, appelle le
matcher
sur undoc
. - Les correspondances retournées sont des tuples
(match_id, start, end)
. - Pour ajouter un exemple à la liste des exemples d'apprentissage, tu peux
utiliser
TRAINING_DATA.append()
.
Dans cet exercice, tu vas préparer un pipeline spaCy pour entrainer l'entity
recognizer à reconnaitre des entités "GADGET"
dans un texte – par exemple,
"iPhone X".
- Crée un modèle vide
"fr"
, par exemple avec la méthodespacy.blank
. - Crée un nouvel entity recognizer en utilisant
nlp.create_pipe
et ajoute-le au pipeline. - Ajoute le nouveau label
"GADGET"
à l'entity recognizer en utilisant la méthodeadd_label
sur le composant de pipeline.
- Pour créer un entity recognizer vide, tu peux appeler
nlp.create_pipe
avec la chaine"ner"
. - Pour ajouter le composant au pipeline, utilise la méthode
nlp.add_pipe
. - La méthode
add_label
est une méthode du composant de pipeline entity recognizer, stocké dans la variablener
. Pour lui ajouter un label, tu peux appelerner.add_label
avec la chaine de caractères du label, par exemplener.add_label("SOME_LABEL")
.
Ecrivons une boucle simple d'apprentissage à partir de zéro !
Le pipeline que tu as créé dans l'exercice précédent est disponible en tant
qu'objet nlp
. Il contient déjà l'entity recognizer avec le label ajouté
"GADGET"
.
Le petit jeu d'exemples labellisés que tu as créé précédemment est disponible en
tant que TRAINING_DATA
. Pour voir les exemples, tu peux les imprimer dans ton
script.
- Appelle
nlp.begin_training
, crée une boucle d'apprentissage pour 10 itérations et mélange les données d'apprentissage. - Crée des lots de données d'apprentissage avec
spacy.util.minibatch
et itère sur les lots. - Convertis les tuples
(text, annotations)
en listes detexts
etannotations
. - Pour chaque lot, utilise
nlp.update
pour actualiser le modèle avec les textes et les annotations.
- Pour commencer l'apprentissage et réinitialiser les poids, appelle la méthode
nlp.begin_training()
. - Pour diviser les données d'apprentissage divide en lots, appelle la fonction
spacy.util.minibatch
sur la liste des exemples d'apprentissage.
Voyons comment le modèle se comporte sur des données inconnues ! Pour accélérer
un peu les choses, nous avons déjà fait tourner un modèle entrainé pour le label
"GADGET"
sur du texte. Voici certains des résultats :
Text | Entities |
---|---|
Apple ralentit l'iPhone 8 et l'iPhone X - comment arrêter ça | (iPhone 8, iPhone X) |
J'ai enfin compris à quoi servait l'encoche sur l'iPhone X | (iPhone X,) |
Tout ce que vous devez savoir à propos du Samsung Galaxy S9 | (Samsung Galaxy,) |
Vous voulez comparer les modèles d'iPad ? Voici comment se présente la gamme 2020 | (iPad,) |
L'iPhone 8 et l'iPhone 8 Plus sont des smartphones conçus, développés et vendus by Apple | (iPhone 8, iPhone 8) |
quel est l'ipad le moins cher, parmi les ipad pro ??? | (ipad, ipad) |
Les Samsung Galaxy sont une série d'appareils informatiques mobiles conçus, fabriqués et vendus par Samsung Electronics | (Samsung Galaxy,) |
Parmi toutes les entités présentes dans les textes, combien le modèle en a-t-il identifiées correctement ? Rappelle-toi que que les spans d'entités incomplets comptent aussi comme des erreurs ! Astuce : Compte le nombre d'entités que le modèle aurait dû prédire. Ensuite compte le nombre d'entités qu'il a effectivement prédites correctement et divise-le par le nombre total d'entités correctes.
Essaie de compter le nombre d'entités correctement prédites et divise-le par le nombre total d'entités correctes que le modèle aurait dû prédire.
Essaie de compter le nombre d'entités correctement prédites et divise-le par le nombre total d'entités correctes que le modèle aurait dû prédire.
Sur nos données de test, le modèle a atteint une justesse de 70 %.
Essaie de compter le nombre d'entités correctement prédites et divise-le par le nombre total d'entités correctes que le modèle aurait dû prédire.
Voici un extrait d'un jeu d'apprentissage qui labellise le type d'entité
TOURIST_DESTINATION
dans des évaluations de voyageurs.
TRAINING_DATA = [
(
"je suis allé à amsterdem l'an dernier et les canaux étaient magnifiques",
{"entities": [(15, 24, "TOURIST_DESTINATION")]},
),
(
"Tu devrais visiter Paris au moins une fois dans ta vie, mais la Tour Eiffel ce n'est pas terrible",
{"entities": [(19, 24, "TOURIST_DESTINATION")]},
),
("There's also a Paris in Arkansas, lol", {"entities": []}),
(
"Berlin est la destination parfaite pour les vacances d'été : beaucoup de parcs, une vie nocturne trépidante et de la bière pas chère !",
{"entities": [(0, 6, "TOURIST_DESTINATION")]},
),
]
Pourquoi ces données et ce schéma d'étiquetage sont-ils problématiques ?
Il serait bien plus judicieux de labelliser uniquement avec le label "GPE"
(entité géopolitique) ou "LOCATION"
(lieu) et ensuite d'utiliser un système à
base de règles pour déterminer si l'entité est ou non une destination
touristique dans ce contexte. Par exemple, tu pourrais recouper les types
d'entités avec une base de connaissances ou les chercher dans un wiki de voyage.
Même s'il est possible que Paris, AK soit aussi une attraction touristique, cela ne fait que souligner à quel point le schéma de labellisation est subjectif et à quel point il sera difficile de décider si le label s'applique ou non. De ce fait, cette distinction sera très difficile à apprendre pour l'entity recognizer.
Même des mots très peu communs ou des mots mal orthographiés peuvent être labellisés comme entités. En fait, la capacité à prédire des catégories sur des textes mal orthographiés en se basant sur le contexte est l'un des principaux avantages des reconnaissances statistiques d'entités nommées.
- Réécris le
TRAINING_DATA
pour utiliser uniquement le label"GPE"
(villes, états, pays) au lieu de"TOURIST_DESTINATION"
. - N'oublie pas d'ajouter les tuples pour les entités
"GPE"
qui n'avaient pas été labellisées dans les anciennes données.
- Pour les spans qui sont déjà labellisés, tu as juste à changer le nom du label
de
"TOURIST_DESTINATION"
en"GPE"
. - Un texte comporte une ville et un état qui ne sont pas encore labellisés. Pour
ajouter les spans des entités, compte les caractères pour trouver où commence
et où finit le span. Ensuite ajoute les tuples
(start, end, label)
aux entités.
Voici un petit échantillon d'un jeu de données créé pour entrainer un nouveau
type d'entité "WEBSITE"
. Le jeu de données original contient quelques milliers
de phrases. Dans cet exercice, tu vas effectuer la labellisation à la main. En
situation réelle, tu l'automatiserais probablement en utilisant un outil
d'annotations - par exemple, Brat, une solution
open-source populaire, ou Prodigy, notre propre outil
d'annotations qui s'intègre avec spaCy.
- Complète les positions des entités
"WEBSITE"
dans les données. Tu peux utiliserlen()
si tu ne veux pas compter les caractères.
- Les positions de début et de fin d'un span d'entité sont les positions des
caractères dans le texte. Par exemple, si une entité commence à la position 5,
sa position de départ est
5
. N'oublie pas que les positions de fin sont exclues - donc10
signifie jusqu'au caractère 10.
Un modèle a été entrainé avec les données que tu viens d'étiqueter, plus
quelques milliers d'autres exemples. Après l'apprentissage, il fait de
l'excellent travail sur "WEBSITE"
, mais ne reconnait plus "PERSON"
. A quoi
cela pourrait-il être dû ?
Il est parfaitement possible pour un modèle d'apprendre des catégories très différentes. Par exemple, le modèle anglais pré-entrainé de spaCy est capable de reconnaitre des personnes, mais aussi des organisations ou des pourcentages.
Si des entités "PERSON"
sont présentes dans les données d'apprentissage mais
ne sont pas labellisées, le modèle va apprendre qu'elles ne doivent pas être
prédites. De même, si un type d'entité existante n'est pas présent dans les
données d'apprentissage, le modèle peut les "oublier" et arrêter de les
prédire.
Si les hyperparamètres peuvent influer sur la justesse d'un modèle, ils ne sont probablement pas le problème ici.
- Actualise les données d'apprentissage pour inclure des annotations pour les
entités
"PERSON"
"PewDiePie" et "Alexis Ohanian".
- Pour ajouter d'autres entités, ajoute un autre tuple
(start, end, label)
à la liste.