Entraîner votre premier modèle sur vos annotations
Lancez l'étude d'exemple d'avis de Potato sur un portable sans GPU, étiquetez 120 avis avec le simulateur, entraînez sklearn-text et découvrez les pré-étiquettes du modèle.
Nouveauté de la v2.14.0
Ce tutoriel entraîne un classifieur de sentiment sur les étiquettes d'une étude d'exemple, puis montre les réponses du classifieur au prochain annotateur sous forme de pré-étiquettes. Il s'adresse à un responsable d'étude qui essaie l'entraînement de modèles de Potato pour la première fois, et chaque étape tourne sur un portable sans GPU et sans autre installation que Potato lui-même. Vous démarrez le projet d'avis d'exemple de Potato, vous faites étiqueter 120 des 160 avis du projet par le simulateur d'utilisateurs, vous entraînez sklearn-text depuis la page Training de l'administration, vous lisez le score sur items réservés de l'exécution, puis vous vous connectez en nouvel annotateur pour voir les réponses du modèle. Pour ce que fait chaque partie de la boucle en général, consultez la vue d'ensemble de l'entraînement de modèles.
Installer Potato et le projet d'exemple
Le tutoriel utilise sklearn-text, un module d'entraînement qui transforme chaque avis en caractéristiques TF-IDF et ajuste un classifieur par régression logistique. sklearn-text ne demande aucune installation supplémentaire, car scikit-learn fait partie des dépendances de base de Potato. Le projet d'exemple se trouve dans le dépôt GitHub de Potato plutôt que dans le paquet pip, donc installez Potato et clonez le dépôt.
pip install --upgrade potato-annotation
git clone https://github.com/davidjurgens/potato.git
cd potatoToutes les commandes ci-dessous s'exécutent depuis la racine du dépôt. Le dossier du projet examples/ai-assisted/model-training/ contient trois fichiers.
config.yamlest la configuration de l'étude, avec les commandes de ce tutoriel dans ses commentaires.data/reviews.jsoncontient 160 avis de produits synthétiques, un objet JSON par ligne avec unidet untext.data/gold.jsondonne l'étiquette correcte de chaque avis. Le simulateur répond à partir de ce fichier.
La configuration d'exemple
La configuration définit un schéma radio nommé sentiment avec les étiquettes positive et negative, et active l'entraînement de modèles. Le bloc ci-dessous est le fichier livré sans ses commentaires, et ce fichier passe python -m potato.validate_cli --strict sans modification.
annotation_task_name: "Review Sentiment (model training demo)"
data_files:
- "data/reviews.json"
item_properties:
id_key: "id"
text_key: "text"
task_dir: "."
output_annotation_dir: "annotation_output"
require_password: false
admin_api_key: "demo-admin-key"
num_annotators_per_item: 1
annotation_schemes:
- annotation_type: "radio"
name: "sentiment"
description: "Is this review positive or negative?"
labels:
- "positive"
- "negative"
sequential_key_binding: true
model_training:
enabled: true
writeback:
schemas: ["sentiment"]
include_unlabeled: true
min_confidence: 0.6Quatre paramètres façonnent le tutoriel.
num_annotators_per_item: 1donne une étiquette à chaque avis. Trois annotateurs simulés avec 40 avis chacun couvrent alors 120 avis différents et en laissent 40 sans étiquette pour le modèle.require_password: falsepermet à un nouvel annotateur de se connecter avec un simple nom d'utilisateur. La dernière étape se connecte ainsi.admin_api_key: "demo-admin-key"ouvre les pages d'administration. Remplacez cette clé sur tout serveur auquel d'autres personnes ont accès.model_trainingenregistre les routes/admin/training. Le blocwritebackmontre aux annotateurs les prédictions du schémasentiment, et la section sur l'écriture en retour ci-dessous explique chaque clé.
Démarrer le serveur sur le port 8000
Démarrez Potato avec la configuration d'exemple.
potato start examples/ai-assisted/model-training/config.yaml -p 8000Le serveur charge les 160 avis et sert la page d'annotation à l'adresse http://localhost:8000. Si le port 8000 est pris sur votre machine, donnez un autre port à -p et utilisez ce port dans toutes les URL ci-dessous.
Étiqueter 120 avis avec le simulateur
Le modèle a besoin d'étiquettes humaines pour apprendre. Le simulateur d'utilisateurs remplace trois annotateurs. Chaque annotateur simulé répond à partir du fichier de référence et donne la bonne réponse la plupart du temps. Lancez le simulateur dans un second terminal, depuis la racine du dépôt.
python -m potato.simulator --server http://localhost:8000 --users 3 \
--strategy gold_standard --competence good=1.0 --max-annotations 40 \
--gold-file examples/ai-assisted/model-training/data/gold.json \
--sequential --fast-mode --no-export--strategy gold_standard fait répondre chaque annotateur simulé à partir de gold.json, et --competence good=1.0 donne aux trois annotateurs le profil good du simulateur. Un annotateur good tire une exactitude entre 0,80 et 0,90 et répond correctement à chaque avis avec cette probabilité. Les étiquettes contiennent donc des erreurs, comme celles d'une vraie équipe. --sequential fait passer les trois annotateurs l'un après l'autre, --fast-mode supprime les pauses entre les réponses, et --no-export évite d'écrire les fichiers de résultats propres au simulateur. Le simulateur termine en environ deux secondes et affiche un récapitulatif. Vérifiez que le récapitulatif indique Total annotations: 120 avant de continuer. Vous pouvez aussi étiqueter des avis à la main sur http://localhost:8000. sklearn-text refuse de s'ajuster avec moins de 10 items étiquetés dans la partition train.
Ouvrir la page Training avec la clé d'administration
La page Training demande une session d'administrateur. Ouvrez http://localhost:8000/admin, saisissez demo-admin-key quand la page demande la clé d'API, puis ouvrez http://localhost:8000/admin/training.
La page Training après deux exécutions de sklearn-text sur le projet d'exemple
Le panneau Start a run en haut contient toute la préparation. Schema liste l'unique schéma du projet, sentiment (radio). Trainer liste les 38 modules d'entraînement, et un module que le projet ne peut pas exécuter porte la raison à côté de son nom, par exemple « not installed ». La page sélectionne sklearn-text chaque fois que sklearn-text convient au schéma. Runs on montre l'unique backend du projet, local (this machine).
Entraîner sklearn-text
Laissez Parameters vide pour utiliser les valeurs par défaut du module, puis cliquez sur Train now. L'exécution résout les annotations en une étiquette par avis, répartit les 120 avis étiquetés entre des partitions train, val et test, puis ajuste le modèle dans un processus séparé. Notre exécution a duré 1,5 seconde, et le panneau a affiché « Run finished. » à la fin.
sklearn-text utilise par défaut le TfidfVectorizer de scikit-learn pour les caractéristiques et LogisticRegression pour le classifieur. Avec 50 items ou plus dans la partition train, sklearn-text calibre aussi les confiances du classifieur. La calibration utilise la mise à l'échelle de Platt en dessous de 1 000 items d'entraînement et la régression isotonique à partir de 1 000 items. Le modèle calibré n'est conservé que si la calibration coûte au plus 0,05 d'exactitude sur l'entraînement. La calibration compte ici, parce que l'étape d'écriture en retour compare chaque confiance à min_confidence.
Pour lancer la même exécution depuis un script, envoyez la clé d'administration dans l'en-tête X-API-Key.
curl -X POST -H "X-API-Key: demo-admin-key" -H "Content-Type: application/json" \
http://localhost:8000/admin/training/api/runs \
-d '{"trainer": "sklearn-text", "schemas": ["sentiment"]}'La réponse contient le nouveau run_id et "started": true.
La page de l'exécution et le score sur items réservés
L'exécution terminée apparaît dans le tableau Runs avec la taille de ses partitions train et val et son Held-out score. Cliquez sur l'identifiant de l'exécution pour ouvrir la page de l'exécution à l'adresse /admin/training/runs/<run_id>. Cette page liste l'état, le module, le backend, la taille des partitions, la graine de partition, le score sur items réservés et les paramètres de l'exécution, puis un tableau de chaque métrique et le journal de l'exécution.
Par défaut, une exécution réserve 15 % des items étiquetés pour val et 15 % pour test, et split_seed décide où chaque item atterrit. La partition reste la même d'une exécution à l'autre tant que split_seed garde sa valeur, donc deux exécutions sur les mêmes étiquettes sont évaluées sur les mêmes items. Le score sur items réservés d'une exécution sklearn-text est le macro-F1 sur val. Le macro-F1 fait la moyenne du score F1 de chaque étiquette, ici positive et negative. L'exécution enregistre aussi l'exactitude et le macro-F1 sur test. L'exactitude sur la partition train est enregistrée sous le nom train_accuracy et ne sert jamais de score. Dans notre exécution, le journal indiquait ceci.
[info] Read 76 labelled rows from the train split
[info] Applied sigmoid calibration over 5 folds
[info] Held-out val macro_f1: 0.725La documentation de Potato rapporte une exécution sur le même projet, et le tableau place cette exécution à côté de la nôtre.
| Documentation de Potato | Notre exécution | |
|---|---|---|
| Avis étiquetés | 120 | 120 |
| Items train, val et test | non indiqué | 76, 19 et 25 |
| Score sur items réservés (macro-F1 sur val) | 0,84 | 0,725 |
| Macro-F1 sur test | non indiqué | 0,826 |
| Pré-étiquettes publiées | 80 | 73 |
Prédictions sous min_confidence | 4 | 11 |
Vos chiffres différeront des deux colonnes, car chaque annotateur simulé tire une exactitude au hasard et commet des erreurs différentes. Dans notre exécution, les étiquettes simulées correspondaient à gold.json pour 97 des 120 avis et pour 15 des 19 avis val. Le score sur items réservés mesure l'accord avec les étiquettes de vos annotateurs et non avec une clé de correction, donc les erreurs des annotateurs dans val abaissent le score. Chacune des 73 pré-étiquettes publiées par notre exécution correspondait à gold.json. Sur une vraie étude sans fichier de référence, lisez un score bas sur items réservés comme une raison de vérifier l'accord entre annotateurs avant d'incriminer le modèle.
Activer l'écriture en retour pour le schéma
Les prédictions d'une exécution n'atteignent les annotateurs que par l'écriture en retour. La configuration d'exemple active déjà l'écriture en retour pour le schéma sentiment. Pour votre propre projet, ajoutez ce bloc sous model_training dans la configuration et redémarrez le serveur.
model_training:
enabled: true
writeback:
schemas: ["sentiment"]
include_unlabeled: true
min_confidence: 0.6writeback.schemas nomme les schémas dont les prédictions sont montrées aux annotateurs. La liste est vide par défaut, donc activer l'entraînement ne change rien sur la page d'annotation tant que vous ne nommez pas un schéma. include_unlabeled: true fait prédire à chaque exécution les avis que personne n'a étiquetés, en plus des avis val et test. Sans include_unlabeled, une exécution ne prédit que sur les avis val et test, et ces avis ont déjà une étiquette humaine. min_confidence: 0.6 garde une prédiction hors de la page d'annotation quand la confiance du modèle tombe sous 0,6. Potato conserve tout de même la prédiction.
L'écriture en retour s'exécute après chaque exécution réussie et ignore tout item de la partition train de l'exécution. Dans notre exécution, le modèle a prédit sur 84 avis (19 val, 25 test et les 40 sans étiquette), 11 prédictions sont tombées sous 0,6, et l'exécution a publié les 73 autres. Le champ writeback de GET /admin/training/api/status donne les mêmes comptes, avec le résumé « Published 73 prediction(s) as prelabels. ». Les prédictions conservées sont réécrites au démarrage du serveur, donc les pré-étiquettes survivent à un redémarrage. Pour retirer les pré-étiquettes d'une exécution des items, envoyez DELETE /admin/training/api/runs/<run_id>/predictions.
Une pré-étiquette vue par un nouvel annotateur
Ouvrez http://localhost:8000 dans une fenêtre de navigation privée et connectez-vous avec un nom d'utilisateur que personne n'a utilisé, par exemple newannotator. Chaque avis étiqueté a déjà sa seule étiquette, donc le nouvel annotateur reçoit les 40 avis sans étiquette, et le compteur de progression de notre exécution indiquait 0/40. Notre premier avis était « The toaster: Disappointed, it stopped working within a week. Much smaller than the photos suggest. » avec Negative déjà sélectionné, à une confiance de 0,68.
Un avis qui s'ouvre avec la réponse du modèle sélectionnée, avant que l'annotateur n'ait rien enregistré
La pré-étiquette n'est pas enregistrée tant que l'annotateur se contente de regarder l'avis, et la pastille d'état indique « Not labeled » jusqu'à ce que l'annotateur enregistre une réponse. La réponse du modèle devient celle de l'annotateur quand celui-ci change la sélection ou clique sur Next. Dans notre exécution, les 5 avis sans étiquette dont la prédiction était tombée sous min_confidence se sont ouverts sans rien de sélectionné. Un annotateur tenu à l'écart de l'aide automatique avec ai_support.holdout ne voit aucune pré-étiquette. Les pré-étiquettes attirent les annotateurs vers la réponse du modèle, donc activez l'écriture en retour une fois le score sur items réservés assez élevé pour qu'on s'y fie, et repérez les annotateurs qui acceptent toutes les pré-étiquettes avec les contrôles de détecter les pré-étiquettes validées sans examen.
Étapes suivantes
Le même projet permet encore quelques expériences avant de passer à vos propres données.
- Changer un paramètre. Saisissez
{"vectorizer_kwargs": {"ngram_range": [1, 2]}}dans Parameters et entraînez à nouveau pour ajouter des paires de mots aux caractéristiques. Notre seconde exécution avec paires de mots a obtenu 0,774 de macro-F1 sur val avec la même partition et a publié 74 pré-étiquettes. Un nom de paramètre quesklearn-textn'accepte pas est refusé, avec la liste des noms que le module accepte. - Essayer un transformeur.
hf-text-classification(pip install "potato-annotation[train-text]") etsetfit(pip install "potato-annotation[embeddings]") apprennent le même schéma, et la page des modules d'entraînement donne les paramètres de chaque module. - Fermer la boucle. Le modèle dans la boucle ajoute la file de relecture, le réentraînement à l'arrivée des annotations avec
auto_retrainet l'enregistrement de la partition d'une exécution comme version de jeu de données. - Passer à un GPU. Entraîner sur un serveur GPU, un cluster SLURM ou une machine derrière un NAT envoie les mêmes exécutions vers une autre machine.
- Entraîner d'autres types de modèles. Les tutoriels sur l'affinage de LLM, les modèles de vision, les modèles audio et les modèles scientifiques suivent les mêmes étapes avec d'autres modules et d'autres schémas.
Chaque clé utilisée ici figure dans la référence de configuration de l'entraînement de modèles. Lancez la première exécution de votre propre projet en copiant le bloc model_training ci-dessus dans votre configuration et en nommant votre schéma sous writeback.schemas.
Pour aller plus loin
- Vue d'ensemble de l'entraînement de modèles
- Configuration de l'entraînement de modèles
- Modules d'entraînement
- Simulateur d'utilisateurs
- Tableau de bord d'administration
- Apprentissage actif
- Référence de l'entraînement de modèles dans le dépôt Potato, avec les sections complètes sur les paramètres de
sklearn-text, les scores sur items réservés et l'écriture en retour