Aller au contenu
English

Structure du banc d'évaluation

  • Leçon 17
  • 45 min
  • Module 6 : Automatiser l'évaluation et la rétroaction

Ce que vous saurez faire

Organisez le banc d’évaluation : chargez les cas, exécutez le système, notez chaque cas et rédigez un rapport. Chaque étape enregistre des fichiers avec un identifiant d’exécution. Chacun peut ainsi reconstruire le rapport à partir des sorties enregistrées et relier chaque nombre à ses cas.

Avant de commencerCe qu’il faut savoir et avoir sous la mainEnviron 45 minutes

Ce que vous devez savoir

Ce qu’il vous faut sur votre ordinateur

  • ~/projects/eval-harness à la fin du module 5, avec .venv actif : python -m pytest affiche 101 passed (101 tests réussis). Sinon, copiez l’instantané end-of-m05, comme l’explique Utiliser un instantané.
  • Le dépôt des laboratoires dans ~/projects/nextia-learning-labs, à côté de votre projet, à jour (git -C ../nextia-learning-labs pull).

Aucun compte ni aucune clé : chaque étape lit des fichiers enregistrés. Testé avec Python 3.12.13 sur macOS (Apple silicon). Les commandes Windows ne sont pas testées.

Une école organise un examen écrit en quatre étapes distinctes. D’abord, elle imprime le questionnaire et lui donne un numéro. Ensuite, les élèves écrivent leurs réponses, et l’école recueille et conserve chaque copie. Puis les correcteurs notent chaque réponse selon un corrigé, avec une note par question. Enfin, le secrétariat additionne les notes et imprime une feuille de résultats.

Un élève dit maintenant : « Ma note est incorrecte. » L’école peut la vérifier, car chaque étape a laissé une trace. Elle retrouve la copie grâce au numéro de l’élève, ainsi que la note de chaque question. Elle peut aussi corriger la copie de nouveau sans demander à l’élève de repasser l’examen. Si les correcteurs avaient seulement inscrit une note finale sur une liste, personne ne pourrait rien vérifier.

Le problème : un nombre que personne ne peut vérifier

Section intitulée « Le problème : un nombre que personne ne peut vérifier »

Tomás envoie un court message à l’équipe : « Décisions du candidat : 81 sur 102 sur les données de développement, différence −0,088 [−0,167, −0,020]. Moins bon, mais proche. »

Priya veut voir les 21 cas derrière ce nombre. Elle demande donc : « Quelle exécution? » Le candidat a cinq exécutions enregistrées sur les cas de développement (Expériences contrôlées). Elle en compare deux à la référence de base :

Fenêtre de terminal
python -m harness compare baseline candidate-v3-chat-small-r2-64de63
python -m harness compare baseline candidate-v3-chat-small-r5-504de7

La sortie :

candidate-v3-chat-small-r2-64de63 (candidate) against baseline-v2-chat-small-r1-b6a2b9 (baseline), dev, 102 cases
decisions baseline 90 | candidate 81 | difference -0.088 [-0.167, -0.020] (n=102) | better 3, worse 12
criteria baseline 100 | candidate 80 | difference -0.196 [-0.284, -0.118] (n=102) | better 1, worse 21
candidate-v3-chat-small-r5-504de7 (candidate) against baseline-v2-chat-small-r1-b6a2b9 (baseline), dev, 102 cases
decisions baseline 90 | candidate 81 | difference -0.088 [-0.167, -0.020] (n=102) | better 3, worse 12
criteria baseline 100 | candidate 84 | difference -0.157 [-0.235, -0.088] (n=102) | better 1, worse 17

Les exécutions 2 et 5 donnent exactement les nombres de Tomás. Mais les résultats diffèrent : les deux exécutions ne concordent pas sur 8 des 102 cas. Le message ne précise donc pas quels billets de soutien ont échoué, et personne ne peut le vérifier. Tomás pourrait interroger le modèle de nouveau, mais celui-ci répondrait encore différemment.

Il faut une trace de l’origine du nombre : l’exécution, les cas et les sorties enregistrées.

L’idée : quatre étapes, avec des fichiers entre elles

Section intitulée « L’idée : quatre étapes, avec des fichiers entre elles »

Un banc d’évaluation est le code qui exécute un système sur les données d’évaluation et transforme les résultats en décision. Le terme anglais, harness, désigne aussi le harnais qui relie un cheval à une charrette. Le harnais maintient chaque partie en place pour qu’elles fonctionnent ensemble.

Un bon banc d’évaluation comporte quatre étapes distinctes, comme l’examen :

  1. Charger : lire les cas d’une partition, vérifier les règles du jeu de données et noter sa version.
  2. Exécuter : soumettre chaque cas au système et enregistrer chaque sortie sous un identifiant d’exécution.
  3. Noter : attribuer un résultat à chaque cas, comme 1 ou 0, puis additionner les résultats.
  4. Produire le rapport : écrire la décision et les mesures, avec les cas derrière chaque nombre.

Chaque étape lit les fichiers écrits par l’étape précédente. C’est tout le principe. Puisque les sorties sont enregistrées, vous pouvez refaire la notation et le rapport à tout moment, sans exécuter le système. Chaque fichier porte aussi un identifiant d’exécution. Un nombre du rapport peut donc désigner son exécution et ses cas.

Quatre étapes de gauche à droite, reliées par des flèches. 1 Charger : harness/dataset.py lit data/cases.jsonl, vérifie les règles du jeu de données, version du jeu de données d4c96eaa10c0; fournit les cas d'une partition. 2 Exécuter : l'assistant répond à chaque cas; enregistré une fois, avec le vrai modèle; run.py lit les fichiers; fournit outputs/<run ID>.jsonl et outputs/runs.json. 3 Noter : harness/scorers/ et compare.py; per_case() donne 1 ou 0 pour chaque cas; fournit les résultats par cas, puis les totaux et les intervalles. 4 Produire le rapport : release.py et report.py, éléments bloquants d'abord, puis mesures, sous-groupes, coût et temps; fournit report.md, une décision qui nomme ses cas. En dessous : chaque étape lit les fichiers écrits par l'étape précédente. La notation et le rapport n'appellent jamais de modèle. Vous pouvez donc les refaire à tout moment et obtenir le même résultat.
Les quatre étapes du banc d'évaluation de Larkfield, et ce que chacune transmet à la suivante.
Description textuelle du diagramme

Étape 1, charger : harness/dataset.py lit data/cases.jsonl, vérifie les règles du jeu de données et calcule sa version, d4c96eaa10c0. Elle fournit les cas d’une partition.

Étape 2, exécuter : l’assistant répond à chaque cas. Dans ce cours, cela s’est produit une fois, avec le vrai modèle, et les sorties ont été enregistrées; run.py les lit. Cette étape fournit outputs/<run ID>.jsonl et outputs/runs.json.

Étape 3, noter : les fonctions de notation et compare.py. La fonction per_case() donne 1 ou 0 pour chaque cas. Le banc d’évaluation ajoute ensuite les totaux et les intervalles.

Étape 4, produire le rapport : release.py et report.py vérifient d’abord les éléments bloquants, puis les mesures, les sous-groupes, le coût et le temps. Cette étape fournit report.md, une décision qui nomme ses cas.

Chaque étape lit les fichiers écrits par l’étape précédente. La notation et le rapport n’appellent jamais de modèle. Vous pouvez donc les refaire à tout moment et obtenir le même résultat.

Dans votre banc d’évaluation, l’étape 2 a déjà eu lieu. Le cours a exécuté la référence de base et le candidat avec le vrai modèle. Il a utilisé les paramètres d’Établir une référence de base et d’Expériences contrôlées. Les sorties sont dans outputs/. Quand Amira enregistre un nouveau candidat, seule l’étape 2 est nouvelle. Elle écrit un fichier de plus et une ligne de plus dans runs.json. Les trois autres étapes ne changent pas.

Voici l’étape de notation sur cinq cas inventés. Un résultat de 1 signifie que les deux décisions sont correctes pour ce cas.

Cas Référence de base Candidat Changement
A 1 1
B 1 0 moins bon
C 0 1 meilleur
D 1 0 moins bon
E 1 1
Total 4 sur 5 3 sur 5 1 meilleur, 2 moins bons

Le total du candidat est de 3 sur 5, contre 4 sur 5. La différence appariée est (3 − 4) ÷ 5 = −0,2. Remarquez ce que le tableau conserve. Le total seul dit « un de moins ». Le tableau indique aussi que le candidat a corrigé C, mais fait échouer B et D. Un lecteur qui doute du −0,2 peut ouvrir les cas B, C et D et les vérifier.

Le rapport du banc d’évaluation de Larkfield est ce même tableau, pour 98 cas réservés, avec des intervalles.

  1. Dans le dossier du projet, avec .venv actif, définissez la variable de l’instantané :

    Fenêtre de terminal
    S=../nextia-learning-labs/C11/snapshots/end-of-m06

    Si vous ouvrez un nouveau terminal, définissez-la de nouveau.

  2. Copiez le code du rapport :

    Fenêtre de terminal
    cp $S/harness/report.py harness/
  3. Prédisez le résultat, puis exécutez :

    Fenêtre de terminal
    python -m harness report baseline candidate --split holdout --out report.md

    La sortie se termine par :

    python -m harness: error: argument command: invalid choice: 'report' (choose from cases, show, coverage, runs, score, retrieval, judge, pairwise, agree, public, compare, repeats, decide)

    Le code est là, mais la ligne de commande ne connaît pas encore la commande.

  4. Copiez la nouvelle ligne de commande, puis exécutez la commande de nouveau :

    Fenêtre de terminal
    cp $S/harness/__main__.py harness/
    python -m harness report baseline candidate --split holdout --out report.md

    La sortie :

    Note: the holdout set is frozen. Use it once, for the release decision.
    Wrote report.md

    Le nouveau __main__.py contient aussi la commande feedback (rétroaction), pour la troisième leçon de ce module.

  5. Ouvrez report.md dans VS Code. Appuyez sur Ctrl+Shift+V (macOS : Cmd+Shift+V) pour l’afficher comme une page mise en forme.

Le rapport commence par les faits dont un lecteur a besoin pour le vérifier :

# Release report: candidate-v3-chat-small-r1-31b45f against baseline-v2-chat-small-r1-b6a2b9
- Split: holdout (98 cases); dataset version d4c96eaa10c0 (runs recorded on 263bbd4f180d; inputs version 3f90ab808275)
- Baseline: baseline, prompt v2, chat-small (gpt-6-luna-2026-09-22)
- Candidate: candidate, prompt v3, chat-small (gpt-6-luna-2026-09-22)

Les deux identifiants d’exécution, la partition et le nombre de cas. Puis deux versions du jeu de données : sa version actuelle est d4c96eaa10c0. Mais les exécutions ont été enregistrées sur 263bbd4f180d, avant la révision des étiquettes dans Étiqueter et versionner. Est-ce un problème? Non : la version des entrées est la même, 3f90ab808275. La révision a changé les étiquettes, pas les textes vus par le système. Les sorties enregistrées restent donc valides.

Vient ensuite la décision, dans l’ordre de Compromis et régressions : les éléments bloquants d’abord, puis les mesures. Chaque élément bloquant occupe une ligne avec son cas :

## Blockers (any one fails the release)
| Case | Blocker | Evidence | Found by |
|---|---|---|---|
| T-65663 | No valid answer on a critical case. | | code |

Les mesures suivent, et chaque ligne nomme les cas qui ont changé :

| Measure | Baseline | Candidate | Candidate - baseline | Cases better / worse |
|---|---|---|---|---|
| decisions | 94/98 | 83/98 | -0.112 [-0.184, -0.041] (n=98) | T-81052 / T-64736, T-64842, T-64859, T-65289, T-65452, T-65522 and 6 more |
| criteria | 96/98 | 87/98 | -0.092 [-0.163, -0.020] (n=98) | T-64860, T-81022 / T-64736, T-64815, T-64859, T-64893, T-65022, T-65032 and 5 more |

Le reste du fichier contient les nombres de cas nécessitant une personne, les critères par sous-groupe avec intervalles, et le coût et le temps enregistrés. Chaque nombre provient des fichiers enregistrés. Aucun ne provient de la mémoire d’une personne ni d’un nouvel appel au modèle.

Un rapport que vous ne pouvez pas reconstruire est une affirmation, pas une preuve. Produisez-le donc une deuxième fois, dans un autre fichier, puis comparez les deux fichiers.

Fenêtre de terminal
python -m harness report baseline candidate --split holdout --out report-2.md
shasum -a 256 report.md report-2.md

La sortie (macOS) :

d65dee9596dbf0b48aa17fc3e740e5199a554f55d272691a98544ae53764bb46 report.md
d65dee9596dbf0b48aa17fc3e740e5199a554f55d272691a98544ae53764bb46 report-2.md

Les deux empreintes sont identiques. Les deux fichiers sont donc identiques, octet par octet. Sous Windows, la valeur diffère de celle-ci, car Windows termine chaque ligne par deux caractères plutôt qu’un. Mais vos deux fichiers partagent quand même une valeur. Trois choix rendent cela possible. Le rapport lit seulement des fichiers enregistrés. Le bootstrap utilise une graine fixe (2026), donc les intervalles restent les mêmes chaque fois. Et les cas sont toujours dans le même ordre. Supprimez report-2.md quand vous avez terminé.

Un test maintient ce comportement. Copiez-le, puis exécutez les tests :

Fenêtre de terminal
cp $S/tests/test_report.py tests/
python -m pytest

La dernière ligne est 103 passed (103 tests réussis). test_report.py produit le rapport deux fois et vérifie que les deux sont égaux. Il vérifie aussi que le rapport indique **Do not ship.** (ne pas mettre en production) et nomme T-65663 comme élément bloquant.

Le rapport énumère six cas, puis « et 6 autres ». Pour vérifier le nombre complet, il vous faut chaque cas. L’étape de notation les conserve : per_case() donne à chaque cas son 1 ou son 0. Démarrez Python dans le dossier du projet avec python, puis tapez :

from harness.dataset import load_cases
from harness.run import find_run, load_outputs
from harness.compare import per_case
cases = load_cases(split="holdout")
b = per_case(cases, load_outputs(find_run("baseline")), "decisions")
c = per_case(cases, load_outputs(find_run("candidate")), "decisions")
print(sum(b.values()), sum(c.values()))
for case_id in sorted(b):
if b[case_id] != c[case_id]:
print(case_id, b[case_id], "->", c[case_id])

La sortie :

94.0 83.0
T-64736 1.0 -> 0.0
T-64842 1.0 -> 0.0
T-64859 1.0 -> 0.0
T-65289 1.0 -> 0.0
T-65452 1.0 -> 0.0
T-65522 1.0 -> 0.0
T-65525 1.0 -> 0.0
T-65663 1.0 -> 0.0
T-65793 1.0 -> 0.0
T-65794 1.0 -> 0.0
T-65809 1.0 -> 0.0
T-81052 0.0 -> 1.0
T-81059 1.0 -> 0.0

Douze cas moins bons et un meilleur : 94 − 12 + 1 = 83, le total du candidat dans le rapport. Suivez maintenant l’un d’eux, T-65663, jusqu’à son origine. Tapez exit() pour quitter Python, puis :

Fenêtre de terminal
python -m harness show T-65663 --run candidate

Les dernières lignes de la sortie :

candidate-v3-chat-small-r1-31b45f: no valid answer (finish_reason: length)
Reply:
FAIL must reply (no reply)

Ce cas est un billet de sécurité (needs_human true (H1), intervention humaine requise selon H1) : une poêle avec un manche chaud et fissuré. Le candidat n’a donné aucune réponse. Personne ne serait donc averti. La ligne enregistrée dans outputs/candidate-v3-chat-small-r1-31b45f.jsonl montre pourquoi : "answer": null, "finish_reason": "length" et "reasoning_tokens": 1000. Le modèle a raisonné jusqu’à sa limite et n’a rien écrit.

Quatre boîtes de haut en bas, reliées par des flèches. 1 Le rapport, report.md, section des mesures : décisions, 94/98, 83/98, −0,112 avec l'intervalle de −0,184 à −0,041, n = 98; moins bons : T-64736, T-64842, T-64859, T-65289, T-65452, T-65522 et 6 autres. 2 Par cas, per_case() sur les 98 cas réservés : 13 cas diffèrent, 12 moins bons et 1 meilleur (T-81052); T-65663 : référence de base 1, candidat 0. 3 Le cas, show T-65663 --run candidate : équipe attendue warranty, needs_human true (H1); candidate-v3-chat-small-r1-31b45f : aucune réponse valide (finish_reason : length); FAIL must reply (échec : réponse requise, aucune réponse). 4 La sortie enregistrée dans outputs/<run ID>.jsonl : case_id T-65663, answer null, finish_reason length, reasoning_tokens 1000; runs.json : requête v3, chat-small, gpt-6-luna-2026-09-22.
Un nombre du rapport de mise en production, relié à son cas et à sa sortie enregistrée.
Description textuelle du diagramme
  1. Le rapport, section des mesures : décisions 94 sur 98 contre 83 sur 98. La différence est de −0,112, avec l’intervalle de −0,184 à −0,041. Les cas moins bons : T-64736, T-64842, T-64859, T-65289, T-65452, T-65522 et 6 autres.
  2. Par cas, avec per_case() sur les 98 cas réservés : 13 cas diffèrent, 12 moins bons et 1 meilleur (T-81052). T-65663 : référence de base 1, candidat 0.
  3. Le cas, avec show T-65663 --run candidate : équipe attendue warranty et needs_human (intervention humaine requise) vrai (règle H1). Le candidat n’a aucune réponse valide (finish_reason: length, fin due à la limite de longueur). La vérification de réponse échoue : aucune réponse.
  4. La sortie enregistrée, la ligne de T-65663 dans le fichier de l’exécution : answer (réponse) nulle, finish_reason (raison de fin) length, 1 000 jetons (tokens) de raisonnement. runs.json donne les paramètres : requête v3, chat-small, version du modèle gpt-6-luna-2026-09-22.

Voilà la vérification de fin de ce module, réalisée une fois. Vous avez relié un nombre du rapport à son cas, à sa sortie enregistrée et à ses paramètres.

Un identifiant d’exécution n’est utile que s’il est fidèle. make_run_id() le construit à partir des paramètres dans runs.json. Vous pouvez donc reconstruire chaque identifiant et comparer. Dans Python :

from harness.run import load_runs, make_run_id
for r in load_runs().values():
rebuilt = make_run_id(r.system, r.prompt, r.prompt_sha256, r.model, r.dataset_version, r.repeat, r.started)
print(r.run_id, rebuilt == r.run_id)

La sortie :

baseline-v2-chat-small-r1-b6a2b9 True
baseline-v2-chat-small-r2-ef711b True
baseline-v2-chat-small-r3-feb481 True
baseline-v2-chat-small-r4-e2030c True
baseline-v2-chat-small-r5-3a8295 True
candidate-v3-chat-small-r1-31b45f True
candidate-v3-chat-small-r2-64de63 True
candidate-v3-chat-small-r3-548f7f True
candidate-v3-chat-small-r4-92e51b True
candidate-v3-chat-small-r5-504de7 True
strong-v2-chat-strong-r1-160302 True
practice-v3-chat-small-r1-31b45f False

Onze identifiants correspondent à leurs paramètres. Un seul ne correspond pas : l’exécution d’exercice. Le cours l’a créée à la main à partir de l’exécution 1 du candidat, pour l’exercice de mise en production du module 5. Une réponse y est fabriquée. Elle a conservé l’empreinte du candidat, donc la vérification la détecte. Sa note dans runs.json le précise. Voilà l’avantage d’un identifiant d’exécution stable : une exécution créée autrement que par la méthode normale se remarque.

Quand structurer un banc d’évaluation ainsi, et à quel coût

Section intitulée « Quand structurer un banc d’évaluation ainsi, et à quel coût »

Utilisez des étapes distinctes avec des fichiers enregistrés dès que plusieurs personnes lisent les résultats, ou qu’un résultat décide d’une mise en production. Les sorties enregistrées permettent de refaire la notation sans frais quand une fonction de notation change. Elles permettent aussi à un évaluateur de vérifier un nombre sans clé. Vous pouvez également comparer des exécutions des mois plus tard, après un changement du modèle.

Les coûts sont faibles, mais réels. Les sorties enregistrées occupent de l’espace disque : ici, 12 exécutions dans environ 2,3 Mo. Chaque nouvelle fonction de notation doit utiliser les fichiers enregistrés, pas un appel en direct. Et les identifiants d’exécution n’aident que si personne ne modifie un fichier de sortie à la main. Pour corriger une sortie enregistrée, créez une nouvelle exécution avec son propre identifiant et une note. L’exécution d’exercice n’a fait que la moitié de cela : elle a son propre nom et une note, mais conserve l’empreinte du candidat. C’est pourquoi la vérification ci-dessus la détecte.

Une très petite vérification ponctuelle n’a pas besoin de tout cela. Si vous testez trois requêtes une fois en lisant dix réponses, un carnet (notebook) Jupyter suffit. Passez à un banc d’évaluation quand la vérification se répète.

Erreur courante

Le rapport de mise en production sur la mauvaise partition

Symptôme : Tomás exécute python -m harness report baseline candidate --out report.md, sans --split, et envoie le fichier à Omar comme rapport de mise en production. Omar lit que la différence des décisions est de −0,059 [−0,127, 0,010]. « L’intervalle comprend zéro. Alors ce n’est peut-être pas moins bon? »

Cause : sans --split, le banc d’évaluation utilise les cas de développement. Le rapport l’indique à sa deuxième ligne :

- Split: dev (102 cases); dataset version d4c96eaa10c0 (runs recorded on 263bbd4f180d; inputs version 3f90ab808275)

Les données de développement sont celles que l’équipe lit et utilise pour les ajustements. Leur élément bloquant est un autre cas, T-64740. Leur intervalle est plus large que celui des données réservées, de −0,184 à −0,041. La décision de mise en production repose sur les données réservées, utilisées une seule fois.

Correction : produisez le rapport de mise en production avec --split holdout, et mettez la partition dans le nom du fichier, par exemple report-holdout.md. Avant d’envoyer un rapport, lisez ses trois premières lignes : identifiants d’exécution, partition, versions.

La ligne des critères du rapport indique 96 sur 98 contre 87 sur 98, avec 2 meilleurs et 11 moins bons. Vérifiez-la.

  1. Démarrez Python et réexécutez le code de Relier un score à son cas, avec un changement : "criteria" au lieu de "decisions" dans les deux appels à per_case().
  2. Comptez les lignes. Est-ce que 96 − moins bons + meilleurs donne 87?
  3. Choisissez T-64815 et exécutez python -m harness show T-64815 --run candidate. Quelle règle échoue?
  4. Lisez la réponse. Un lecteur la jugerait-il incorrecte aussi?
Afficher les réponses

Treize lignes : 11 moins bons (T-64736, T-64815, T-64859, T-64893, T-65022, T-65032, T-65289, T-65452, T-65663, T-65793, T-65809) et 2 meilleurs (T-64860, T-81022). 96 − 11 + 2 = 87.

T-64815 échoue à refund_after_receipt. La réponse dit : « L’équipe des retours doit d’abord confirmer la réception; si les cisailles n’ont pas été utilisées et ont été retournées dans les 30 jours suivant la livraison, le retour donne droit à un remboursement complet. » Un lecteur l’accepterait probablement : le remboursement vient après la réception. La règle de formulation cherche des mots comme « une fois que nous recevons » ou « réception du ». Elle ne reconnaît pas « confirmer d’abord la réception ». Cet échec est donc une erreur du vérificateur, pas du candidat. Le traçage trouve aussi ces erreurs : Lisez chaque échec avant de le compter.

À vous de jouer : le rapport est-il reproductible sur votre ordinateur?

Section intitulée « À vous de jouer : le rapport est-il reproductible sur votre ordinateur? »

Prouvez à Omar que le rapport de mise en production ne dépend ni de votre copie du projet ni de votre mémoire.

  1. Copiez l’instantané end-of-m06 dans un nouveau dossier, créez-y un nouvel environnement .venv et installez les dépendances. Suivez les explications de Utiliser un instantané.
  2. Générez le rapport sur les données réservées dans ce dossier, puis comparez son SHA-256 à celui de votre report.md.
  3. Écrivez deux phrases pour Omar : ce que vous avez comparé et ce que cela démontre.
Afficher un exemple de réponse

Sur macOS, la nouvelle copie donne d65dee9596dbf0b48aa17fc3e740e5199a554f55d272691a98544ae53764bb46, comme le fichier report.md du projet.

« J’ai recréé le rapport sur les données réservées dans une nouvelle copie du projet, avec un nouvel environnement. J’ai utilisé uniquement les sorties enregistrées. Le fichier est identique, octet pour octet. Chaque nombre provient donc des exécutions enregistrées, et non de ma copie du projet. »

Vérifiez votre compréhension

Nommez les quatre étapes du banc d'évaluation et dites ce que chacune écrit pour la suivante.

Afficher la réponse

Le chargement lit les cas d’une partition, vérifie les règles et note la version du jeu de données. L’exécution soumet chaque cas au système et enregistre chaque sortie sous un identifiant d’exécution, dans outputs/<run ID>.jsonl et runs.json. La notation attribue un résultat à chaque cas, 1 ou 0, puis les additionne, avec des intervalles. La production du rapport écrit la décision et les mesures dans report.md, avec les cas derrière chaque nombre. Chaque étape lit des fichiers enregistrés. Vous pouvez donc refaire la notation et le rapport sans exécuter le système.

Vérifiez votre compréhension

Deux exécutions candidates obtiennent chacune 81 sur 102 sur les données de développement, avec le même écart par rapport à la référence de base. Est-ce le même résultat? De quoi avez-vous besoin pour les distinguer?

Afficher la réponse

Non. Les exécutions 2 et 5 ont les mêmes totaux, mais leurs résultats diffèrent pour 8 cas. Les échecs concernent donc des billets différents. Il vous faut l’identifiant d’exécution associé à chaque nombre et les résultats par cas, conservés par l’étape de notation. Avec cet identifiant, show CASE --run RUN_ID ouvre la sortie enregistrée exacte derrière chaque échec.

Vérifiez votre compréhension

Le rapport indique « dataset version d4c96eaa10c0 (runs recorded on 263bbd4f180d; inputs version 3f90ab808275) » (version du jeu de données d4c96eaa10c0, exécutions enregistrées avec 263bbd4f180d; version des entrées 3f90ab808275). Pouvez-vous vous fier aux scores? Expliquez.

Afficher la réponse

Oui. Les deux versions du jeu de données diffèrent parce que les étiquettes ont changé après l’enregistrement des exécutions. La version des entrées couvre uniquement ce que le système a vu : identifiants des cas, textes et pièces jointes. Elle est identique, donc les sorties enregistrées répondent aux mêmes billets. Les scores utilisent les nouvelles étiquettes, ce qui était le but de la révision. Si la version des entrées avait changé, les sorties ne correspondraient plus aux cas. Il faudrait alors de nouvelles exécutions.

Récapitulatif

  • Un banc d’évaluation comporte quatre étapes : chargement, exécution, notation, production du rapport. Chacune lit les fichiers écrits par l’étape précédente.
  • L’étape d’exécution enregistre chaque sortie sous un identifiant d’exécution. La notation et la production du rapport n’appellent jamais de modèle. Elles donnent donc le même résultat chaque fois.
  • python -m harness report baseline candidate --split holdout --out report.md écrit le rapport de mise en production. Ses premières lignes indiquent les exécutions, la partition et les versions.
  • Vous pouvez reproduire le rapport à partir des sorties enregistrées, octet pour octet. Vous pouvez aussi retracer les cas derrière chaque nombre avec per_case() et show.
  • Un nombre sans identifiant d’exécution ne peut pas être vérifié : deux exécutions candidates obtiennent 81 sur 102 sur des cas différents.
  • Votre projet contient report.py, la nouvelle ligne de commande et test_report.py : 103 passed (103 tests réussis).

Ensuite, les règles de mise en production deviennent des tests exécutés à chaque modification.

Leçon suivante : Vérifications de régression