Exercices sur la gestion de fichiers en Python
La gestion des fichiers est une compétence essentielle en programmation. Ces exercices vous permettront de manipuler des fichiers texte pour gérer des données structurées comme des listes de candidats, des résultats de concours, etc.
Gestion d'un concours
Soit un fichier typé intitulé concours.txt qui comporte les enregistrements relatifs aux candidats d'un concours. Chaque enregistrement est composé de : NCIN, NOM, PRENOM, AGE, DECISION (type contenant les identificateurs suivants : admis, refusé, ajourné), et séparé par point virgule (;).
Travail demandé :
- Définir la fonction saisir() qui permet de remplir les données relatives aux candidats dans le fichier concours.txt
- Définir la fonction admis() qui permet créer le fichier admis.txt comportant les données relatives aux candidat admis
- Afin de sélectionner en priorité les candidats admis et âgés moins de 30 ans, créer la fonction attente() qui produira à partir du fichier admis.txt, un nouveau fichier intitulé attente.txt comportant les données relatives aux candidats admis et âgés plus que 30 ans. Une ligne du fichier attente.txt comprend le NCIN, le NOM et PRENOM d'un candidat séparés par point virgule (;).
- Définir la fonction statistiques(dec) qui permet de retourner le pourcentage des candidats pour la décision dec (admis, refusé et ajourné). Exemple : Le pourcentage des candidats admis = (Nombre des candidats admis / Nombre des candidats) *100
- Définir la fonction supprimer() qui supprimera du fichier admis.txt les candidat âgés plus que 30
N.B : On suppose que les fichiers seront mis à la racine du lecteur C.
Chaque ligne du fichier suit le format : NCIN;NOM;PRENOM;AGE;DECISION
def saisir():
"""
Fonction de saisie des candidats dans le fichier concours.txt
"""
new = "O" # O -> oui ; N -> non
fichier = open("concours.txt", "a")
decision = {"a": "admis(e)", "r": "refuse(e)", "aj": "ajourne(e)"}
while new == "O":
cin = input("Saisir le Numero CIN : ")
nom = input("Saisir le Nom : ")
prenom = input("Saisir le prenom : ")
age = input("saisir l age : ")
dec = input("saisir la decision a(admis(e)) r(refuse(e)) aj(ajourne(e)): ")
ligne = cin + ";" + nom + ";" + prenom + ";" + age + ";" + decision[dec] + "\n"
fichier.write(ligne)
new = input("Saisir un nouveau candidat (O / N) ? ")
fichier.close()
def admis():
"""
Crée le fichier admis.txt avec les candidats admis
"""
fichier = open("concours.txt")
dest = open("admis.txt", "a")
for ligne in fichier:
L = ligne.split(";")
if L[4].strip() == "admis(e)":
dest.write(ligne)
fichier.close()
dest.close()
def attente():
"""
Crée le fichier attente.txt avec les candidats admis de plus de 30 ans
"""
fichier = open("admis.txt")
dest = open("attente.txt", "a")
for ligne in fichier:
L = ligne.split(";")
if int(L[3]) >= 30:
enreg = L[0] + ";" + L[1] + ";" + L[2] + "\n"
dest.write(enreg)
fichier.close()
dest.close()
def statistiques(dec):
"""
Calcule le pourcentage de candidats pour une décision donnée
Paramètres:
dec: "admis", "refuse" ou "ajourne"
Retourne:
Pourcentage correspondant
"""
fichier = open("concours.txt")
L = fichier.readlines()
fichier.close()
L1 = [] # candidats admis
L2 = [] # candidats refuses
L3 = [] # candidats ajournes
for ligne in L:
L = ligne.split(";")
if L[4].strip() == "admis(e)":
L1.append(ligne)
elif L[4].strip() == "refuse(e)":
L2.append(ligne)
else:
L3.append(ligne)
if dec == "admis":
return (len(L1) / len(L)) * 100
elif dec == "refuse":
return (len(L2) / len(L)) * 100
else:
return (len(L3) / len(L)) * 100
def supprimer():
"""
Supprime du fichier admis.txt les candidats âgés de plus de 30 ans
"""
fichier = open("admis.txt")
candidat = [] # contient les candidats restants
for ligne in fichier:
L = ligne.split(";")
if int(L[3]) < 30:
candidat.append(ligne)
fichier.close()
# Réécrire la nouvelle liste
fichier = open("admis.txt", "w")
fichier.writelines(candidat)
fichier.close()
# Exemple d'utilisation
# saisir()
# admis()
# attente()
# print(statistiques("admis"))
# supprimer()123456;Dupont;Jean;25;admis(e) 789012;Martin;Marie;32;admis(e) 345678;Petit;Paul;28;refuse(e) 901234;Durand;Sophie;35;admis(e)
Orientation des bacheliers
Après la réussite au baccalauréat, les meilleurs bacheliers sont orientés vers les classes préparatoires aux grandes écoles. En effet, la priorité est à celui qui a le score (nombre de points) le plus élevé. Ce score est appelé formule globale.
Les élèves admissibles seront classés par ordre décroissant selon la formule globale. Puis, une fois classés, ces bacheliers seront divisés en 4 groupes selon le tableau suivant :
| Groupe | Description | Nb d'étudiants | Répartition |
|---|---|---|---|
| Principale | Liste principale | 30 | 40% (SMA) ; 30% (SMB) ; 20% (PC) ; 10% (SVT) |
| Tranche 1 | Liste d'attente N°1 | 40 | 50% (SMA) ; 25% (SMB) ; 20% (PC) ; 5% (SVT) |
| Tranche 2 | Liste d'attente N°2 | 60 | 40% (SMA) ; 30% (SMB) ; 20% (PC) ; 10% (SVT) |
| Tranche 3 | Liste d'attente N°3 | 50 | 55% (SMA) ; 25% (SMB) ; 20% (PC) |
Dans le répertoire C:/bachelier, on dispose d'un fichier nommé 'PSI.txt' contenant la liste des bacheliers admissibles de la section Physique et sciences industrielles. Dans ce fichier, chaque bachelier est défini par :
- Num_insc : le numéro d'inscription
- NP : le nom et prénom
- FILIERE : le nom de la filière (SMA, SMB, PC ou SVT)
- MG : moyenne générale.
- FS (formule spécifique) : un réel déjà calculé à partir des notes obtenues dans les diverses matières.
- i : un réel = 1 si l'élève est redoublant en BAC et 1.10 sinon
On souhaite réaliser les fonctions suivantes :
- formule_gen() : crée un autre fichier 'PSI_FG.txt' avec les informations : Num_insc, NP, FILIERE et FG. FG = ((5*MG+FS)*i)
- classer() : classe les bacheliers par ordre décroissant selon FG
- generer() : extrait 4 fichiers ('PSI_princ.txt', 'PSI_t1.txt', 'PSI_t2.txt', 'PSI_t3.txt') pour chaque groupe
- afficher(Num_insc) : affiche le groupe d'un candidat donné
def formule_gen():
"""
Crée le fichier PSI_FG.txt avec la formule globale calculée
"""
source = open("PSI.txt")
dest = open("PSI_FG.txt", "a")
for ligne in source:
s = ligne.strip()
tab = s.split(":")
fg = ((5 * float(tab[3]) + float(tab[4])) * float(tab[5]))
etd = str(tab[0]) + ":" + str(tab[1]) + ":" + str(tab[2]) + ":" + str(fg) + "\n"
dest.write(etd)
source.close()
dest.close()
def classer():
"""
Classe les bacheliers par ordre décroissant selon FG (tri par sélection)
"""
source = open("PSI_FG.txt")
L = source.readlines()
# Tri par sélection
for i in range(len(L) - 1):
m = i
for j in range(i + 1, len(L)):
t1 = L[j].strip().split(":")
t2 = L[m].strip().split(":")
if float(t1[3]) > float(t2[3]):
m = j
L[i], L[m] = L[m], L[i]
source.close()
source = open("PSI_FG.txt", "w")
source.writelines(L)
source.close()
def generer():
"""
Génère les 4 fichiers correspondant aux différents groupes
"""
# Séparer les étudiants par filière
l1 = [] # SMA
l2 = [] # SMB
l3 = [] # PC
l4 = [] # SVT
source = open("PSI_FG.txt")
for ligne in source:
t = ligne.split(":")
if t[2] == "SMA":
l1.append(ligne)
elif t[2] == "SMB":
l2.append(ligne)
elif t[2] == "PC":
l3.append(ligne)
else:
l4.append(ligne)
source.close()
# Construction de la liste principale
# Calcul des nombres par filière selon les pourcentages
nb1 = 12 # 40% de 30 = 12 SMA
nb2 = 9 # 30% de 30 = 9 SMB
nb3 = 6 # 20% de 30 = 6 PC
nb4 = 3 # 10% de 30 = 3 SVT
# Indices de début pour chaque filière
isma = 0
ismb = 0
ipc = 0
isvt = 0
# Liste principale
princ = open("PSI_princ.txt", "a")
for i in range(nb1):
if i < len(l1):
princ.write(l1[i])
for i in range(nb2):
if i < len(l2):
princ.write(l2[i])
for i in range(nb3):
if i < len(l3):
princ.write(l3[i])
for i in range(nb4):
if i < len(l4):
princ.write(l4[i])
princ.close()
# Tranche 1
isma = nb1
ismb = nb2
ipc = nb3
isvt = nb4
nb1 = 20 # 50% de 40 = 20 SMA
nb2 = 10 # 25% de 40 = 10 SMB
nb3 = 8 # 20% de 40 = 8 PC
nb4 = 2 # 5% de 40 = 2 SVT
t1 = open("PSI_t1.txt", "a")
for i in range(isma, isma + nb1):
if i < len(l1):
t1.write(l1[i])
for i in range(ismb, ismb + nb2):
if i < len(l2):
t1.write(l2[i])
for i in range(ipc, ipc + nb3):
if i < len(l3):
t1.write(l3[i])
for i in range(isvt, isvt + nb4):
if i < len(l4):
t1.write(l4[i])
t1.close()
# Tranche 2
isma = isma + nb1
ismb = ismb + nb2
ipc = ipc + nb3
isvt = isvt + nb4
nb1 = 24 # 40% de 60 = 24 SMA
nb2 = 18 # 30% de 60 = 18 SMB
nb3 = 12 # 20% de 60 = 12 PC
nb4 = 6 # 10% de 60 = 6 SVT
t2 = open("PSI_t2.txt", "a")
for i in range(isma, isma + nb1):
if i < len(l1):
t2.write(l1[i])
for i in range(ismb, ismb + nb2):
if i < len(l2):
t2.write(l2[i])
for i in range(ipc, ipc + nb3):
if i < len(l3):
t2.write(l3[i])
for i in range(isvt, isvt + nb4):
if i < len(l4):
t2.write(l4[i])
t2.close()
# Tranche 3
isma = isma + nb1
ismb = ismb + nb2
ipc = ipc + nb3
# SVT n'apparaît pas dans la tranche 3
nb1 = 27 # 55% de 50 = 27.5 → arrondi à 27 SMA
nb2 = 12 # 25% de 50 = 12.5 → arrondi à 12 SMB
nb3 = 11 # 20% de 50 = 10 → 11 PC pour compléter
t3 = open("PSI_t3.txt", "a")
for i in range(isma, min(isma + nb1, len(l1))):
t3.write(l1[i])
for i in range(ismb, min(ismb + nb2, len(l2))):
t3.write(l2[i])
for i in range(ipc, min(ipc + nb3, len(l3))):
t3.write(l3[i])
t3.close()
def afficher(Num_insc):
"""
Affiche le groupe d'un candidat à partir de son numéro d'inscription
Paramètres:
Num_insc: numéro d'inscription du candidat
Retourne:
Tuple (etat, tranche) indiquant si trouvé et le groupe
"""
princ = open("PSI_princ.txt")
L1 = princ.readlines()
tr1 = open("PSI_t1.txt")
L2 = tr1.readlines()
tr2 = open("PSI_t2.txt")
L3 = tr2.readlines()
tr3 = open("PSI_t3.txt")
L4 = tr3.readlines()
etat = False
tranche = ""
# Chercher dans la liste principale
for ligne in L1:
if str(Num_insc) == ligne[:len(str(Num_insc))]:
etat = True
tranche = "Liste principale"
break
# Chercher dans la tranche 1
if not etat:
for ligne in L2:
if str(Num_insc) == ligne[:len(str(Num_insc))]:
etat = True
tranche = "Tranche 1"
break
# Chercher dans la tranche 2
if not etat:
for ligne in L3:
if str(Num_insc) == ligne[:len(str(Num_insc))]:
etat = True
tranche = "Tranche 2"
break
# Chercher dans la tranche 3
if not etat:
for ligne in L4:
if str(Num_insc) == ligne[:len(str(Num_insc))]:
etat = True
tranche = "Tranche 3"
break
princ.close()
tr1.close()
tr2.close()
tr3.close()
return (etat, tranche)
# Exemple d'utilisation
# formule_gen()
# classer()
# generer()
# print(afficher("123456"))123456:Dupont Jean:SMA:14.5:8.2:1.10 789012:Martin Marie:SMB:15.2:7.8:1.00 345678:Petit Paul:PC:13.8:9.1:1.10 901234:Durand Sophie:SVT:16.0:6.5:1.00
Ces fonctions illustrent plusieurs concepts importants :
- Lecture et écriture de fichiers texte
- Séparation des données avec split()
- Tri par sélection sur des données complexes
- Filtrage selon des critères multiples
- Recherche dans plusieurs fichiers
- open() permet d'ouvrir un fichier en mode lecture ('r'), écriture ('w') ou ajout ('a').
- Les méthodes readlines() et writelines() permettent de manipuler des listes de lignes.
- split() est essentiel pour séparer les données structurées.
- Toujours fermer les fichiers après utilisation (ou utiliser le context manager 'with').
- La gestion des fichiers permet de traiter des données persistantes entre les exécutions.
Discussion (0)
Soyez le premier à laisser un commentaire !
Laisser un commentaire
Votre commentaire sera visible après modération.