M1 - Python - TD 6 : un sujet d'examen¶

Exercice 1¶

Vos programmes devront reproduire exactement les exemples fournis

Les étudiants du master de Génie Algorithmique Généraliste Avancé, dont vous êtes responsable pédagogique, viennent de passer leur épreuve de COBOL, et les correcteurs vous ont envoyé le fichier notes.txt. L'épreuve comportait 17 questions, de difficultés variées, et on demandait aux correcteurs de noter chaque réponse par un entier de 0 à 4. La note finale sera calculée en appliquant une liste de coefficients, initialement fixée à

coeffs =  [2, 3, 3, 4, 4, 2, 1, 5, 5, 3, 1, 3, 2, 5, 5, 4, 3]

ce qui donne donc une note maximale de 220 points, à ramener sur 20 en arrondissant au demi-point le plus proche.

1) Écrivez une fonction parse(ligne,coeffs) qui convertit une ligne du fichier en un dictionnaire sont les clés sont nom, prenom, note. On considérera que les prénoms forment le premier mot de chaque ligne, alors que les noms de famille peuvent être composés de plusieurs mots, et on vérifiera au moyen d'une clause assert qu'il y a bien une note pour chacune des 17 questions. Par exemple, si ligne = 'Alexandre Garnier de la Coste\t\t3 3 3 4 2 0 1 3 2 1 2 2 0 1 0 0 0', le résultat doit être

{'prenom': 'Alexandre', 'nom': 'Garnier de la Coste', 'note': 8.0}

2) Formez la liste ee des dictionnaires associés à chaque étudiant, et écrivez une fonction tri_nom qui renvoie une liste de lignes NOM Prénom note triée par ordre alphabétique des noms. Par exemple, for l in tri_nom(ee): print(l) devra afficher

ALLAIN Patricia-Josette 9.0
ARNAUD Patricia 13.0
AUBERT Michelle 6.5
BARON DE LOPEZ Alain 6.5
...
VALLET Valentine 9.5
VALLET-HERVÉ Madeleine 10.0
WAGNER Laetitia 11.5

On prendra soin de convertir les noms en majuscules avant de trier, car 'Z'<'a'.

3) On veut maintenant afficher les statistiques de l'examen. Écrivez une fonction stats(ee) qui affiche la moyenne, la médiane, le nombre de reçus, le nombre de collés, et le nombre total d'étudiants :

>>> stats(ee)
Moyenne =  9.625  Mediane =  9.5
45  reçus,  55  collés  sur  100  étudiants.

4) On veut finalement ajouter une clé rang dans les dictionnaires représentant les étudiants. Écrivez une fonction calcule_rangs(ee) qui effectue cette opération. Deux étudiants ayant la même note devront avoir le même rang. Le classement devra être

1   SALMON   Dorothée-Patricia   14.5
2   ARNAUD   Patricia   13.0
2   PAUL   Susan   13.0
4   COHEN   Alain   12.5
4   DU MARCHAND   Adrien   12.5
4   DU ROSSI   René   12.5
7   BOULAY   Bertrand   12.0   
...
92   POULAIN   Denis-Émile   7.0
97   AUBERT   Michelle   6.5
97   BARON DE LOPEZ   Alain   6.5
97   LOPEZ   Nathalie   6.5
97   OLLIVIER   Olivier   6.5

5) Écrivez une fonction qui enregistre les données de la liste ee dans un fichier examen_cobol.csv, avec une ligne par étudiant, comprenant les champs NOM, Prénom, note, rang, séparés par des tabulations, triés par ordre alphabétique des noms :

$ cat examen_cobol.csv
ALLAIN  Patricia-Josette        9.0     61
ARNAUD  Patricia        13.0    2
...
TORRES  Zacharie        7.5     87
VALLET  Valentine       9.5     46
VALLET-HERVÉ    Madeleine       10.0    39
WAGNER  Laetitia        11.5    14

Exercice 2¶

Écrire un générateur Python qui prend comme entrée un flot (un autre générateur, une séquence) numérique, sans longueur spécifiée. La séquence engendrée montre la « tendance » des données source : si les valeurs des données augmentent, le résultat est +1, si diminuent : -1, si égaux : zéro. Il faut que le générateur construit mémorise le dernier élément lu depuis la source. Ainsi, si la séquence source est : 3, 3, 6, -2, 7, 8, 4, 2, 7, 7, 2, 6, 1, 2, 2, 6, ..., le résultat engendré par le générateur doit être : 0, 1, -1, 1, 1, -1, -1, 1, 0, -1, 1, -1, 1, 0, 1, .

>>> bla = iter([ 3, 3, 6, -2, 7, 8, 4, 2, 7, 7, 2, 6, 1, 2, 2, 6])
>>>f(bla)
<generator object f at 0x7fd4fbe33ac0>
>>> list(_)
[0, 1, -1, 1, 1, -1, -1, 1, 0, -1, 1, -1, 1, 0, 1]

Exercice 3¶

Les fonctions suivantes sont à écrire en une ligne. On pourra préalablement importer un ou plusieurs modules.

1) Ecrire une fonction qui prend en entrée une liste et renvoie une liste de couples (x,n) où n est le nombre d'entrées consécutives égales à x.

>>> ll = [2,2,2,2,1,1,2,2,1,1,1,4,4,4,4,2]
>>> f(ll)
[(2, 4), (1, 2), (2, 2), (1, 3), (4, 4), (2, 1)]

2) Ecrire une fonction qui prend en entréee une liste d'entiers et renvoie la liste réarrangée de manière à ce que les entiers impairs soient au début, et les pairs à la fin, en respectant leur ordre initial.

>>> mm = [38, 25, 36, 36, 40, 22, 8, 26, 32, 1, 7, 31, 46, 10, 21, 41, 47, 23, 24, 22, 5, 42, 41, 24, 36, 20, 27, 46, 6, 25]
>>> g(mm)
[25, 1, 7, 31, 21, 41, 47, 23, 5, 41, 27, 25, 38, 36, 36, 40, 22, 8, 26, 32, 46, 10, 24, 22, 42, 24, 36, 20, 46, 6]

3) Ecrire une fonction is_stricly_increasing qui teste si une liste est strictement croissante. On donnera deux versions, une itérative et une récursive.

>>> is_stricly_increasing([1,3,5,5,8,9,9])
False
>>> is_strictly_increasing_rec([2,4,5,9,15,18,25,51])
True
In [ ]: