Corrigé Sujet N°15
- Gestion des Rappels de Vaccination (Cabinet Vétérinaire & SQLite) -
Vous pouvez télécharger les éléments suivants en cliquant sur les boutons associés :
Question 1
Écrire la fonction
normalisation_tel qui prend un numéro de téléphone en argument et renvoie uniquement les chiffres qu'il contient.
Correction : On parcourt chaque caractère du numéro et on ne conserve que ceux qui sont des chiffres, à l'aide de la méthode
isdigit(). Une compréhension de chaîne avec join est la solution la plus concise.
def normalisation_tel(tel):
"""Renvoie uniquement les chiffres du numéro de téléphone."""
return ''.join(c for c in tel if c.isdigit())
# Tests fournis
normalisation_tel("(0)2 12 99 90 12") # >> "0212999012"
normalisation_tel("0.6.12.99.90.12") # >> "0612999012"
normalisation_tel("0-6-12-9-90-1") # >> "06129901"
Question 2
Écrire un jeu de tests permettant de vérifier le bon fonctionnement de la fonction
validation_tel qui valide les numéros de portable français (06/07, 10 chiffres).
Correction : Un bon jeu de tests doit couvrir : un 06 valide, un 07 valide, un fixe (02…), un numéro trop court, un numéro trop long, et un numéro ne commençant pas par 0.
assert validation_tel("0612999012") == True # 06 valide
assert validation_tel("0712999012") == True # 07 valide
assert validation_tel("0212999012") == False # fixe → invalide
assert validation_tel("061299901") == False # 9 chiffres → trop court
assert validation_tel("06129990123") == False # 11 chiffres → trop long
assert validation_tel("1612999012") == False # ne commence pas par 0
print("Tous les tests validation_tel sont passés.")
Question 3
En vous inspirant de
proprietaires_animaux_nes_apres, écrire la fonction consultation_vaccination_chat(date) qui récupère les consultations de vaccination des chats après la date donnée (champs : id_animal, nom_animal, tel_proprietaire, date_consultation), triées par id puis date croissants.
Correction : On effectue deux jointures :
animal → consultation et animal → proprietaire. Les filtres portent sur l'espèce ('chat'), le motif ('vaccination') et la date supérieure au paramètre.
def consultation_vaccination_chat(date):
conn = sqlite3.connect(DB_PATH)
cursor = conn.cursor()
resultat = cursor.execute(
"""
SELECT animal.id, animal.nom, proprietaire.telephone, consultation.date
FROM consultation
JOIN animal ON consultation.id_animal = animal.id
JOIN proprietaire ON animal.id_proprietaire = proprietaire.id
WHERE animal.espece = 'chat'
AND consultation.motif = 'vaccination'
AND consultation.date > ?
ORDER BY animal.id, consultation.date;
""",
(date,),
)
return list(resultat)
Question 4
La fonction
derniere_vaccination ne produit pas les résultats attendus. Expliquer le problème et proposer une correction.
Identification du bug : Dans la boucle, la condition de mise à jour est
elif date < derniere[id_animal][3]. Cette condition est vraie quand la date courante est antérieure à celle déjà enregistrée, ce qui fait qu'on remplace la consultation la plus récente par une plus ancienne. Le dictionnaire finit donc par contenir la première vaccination de chaque chat plutôt que la dernière.
Correction : Il faut inverser la comparaison : mettre à jour uniquement si la date courante est postérieure à celle déjà enregistrée, c'est-à-dire
date > derniere[id_animal][3]. Les dates au format AAAAMMJJ se comparent correctement par ordre lexicographique.
def derniere_vaccination(consultations):
derniere = {}
for consult in consultations:
id_animal = consult[0]
date = consult[3]
if id_animal not in derniere:
derniere[id_animal] = consult
elif date > derniere[id_animal][3]: # CORRECTION : > au lieu de <
derniere[id_animal] = consult
return derniere
Pourquoi la comparaison lexicographique fonctionne-t-elle ici ? Le format AAAAMMJJ (ex :
"20251125") range les dates par année, puis par mois, puis par jour, exactement comme l'ordre alphabétique. Comparer deux dates dans ce format avec < ou > est donc équivalent à une comparaison chronologique.
© 2026 - Clément Legoubé