Programmation Python
Travaux pratiques #1 : programmation orientée objet
Solemane COULIBALY UIE Bamako
Exercice 1 : Gestion d’une bibliothèque
Objectif : Implémenter une classe représentant un livre et une bibliothèque
pour gérer une collection de livres.
Énoncé 1 :
1. Créer une classe Livre avec les attributs suivants :
• titre,
• auteur,
• année,
• disponible (booléen, par défaut True)
2. Ajouter les méthodes :
• emprunter() : change l’état de disponibilité en False si le livre est
disponible.
• rendre() : change l’état de disponibilité en True.
3. Créer une classe Bibliotheque avec :
• Un attribut livres (liste d’objets Livre).
• Une méthode ajouter(livre).
• Une méthode disponibles().
• Une méthode chercher(titre) qui retourne le livre correspondant.
Test du programme :
class Livre:
pass
class Bibliotheque:
pass
# Test du programme
biblio = Bibliotheque()
livre1 = Livre("Python avancé", "Martin Fowler", 2018)
livre2 = Livre("POO en Python", "John Smith", 2020)
[Link](livre1)
[Link](livre2)
1
# simuler la méthode disponibles()
# simuler la méthode emprunter
Exercice 2 : Gestion d’un compte bancaire
Objectif : Manipuler l’encapsulation et les méthodes d’une classe.
Énoncé 2 :
Créer une classe CompteBancaire qui contient :
• Un attribut privé solde.
• Un constructeur initialisant le solde à une valeur donnée (par défaut 0).
• Une méthode deposer(montant) qui ajoute un montant au solde.
• Une méthode retirer(montant) qui soustrait un montant si le solde est
suffisant.
• Une méthode solde() pour afficher le solde actuel.
Test du programme :
class CompteBancaire:
pass
# Test du programme
compte = CompteBancaire(100)
compte.afficher_solde()
[Link](50)
[Link](30)
[Link](200) # Test d'erreur
[Link]()
Exercice 3 : Héritage et polymorphisme
Objectif : Comprendre l’héritage en POO.
Énoncé 3 :
Créer une classe Personne avec :
1. Attributs : nom et age.
2. Une méthode se_presenter() qui affiche “Je suis {nom}, j’ai {age} ans”.
Créer une classe Etudiant qui hérite de Personne et ajoute :
• Un attribut filiere.
• Une méthode se_presenter() qui affiche aussi la filière.
Test du programme :
class Personne:
pass
2
class Etudiant(Personne):
pass
# Test du programme
personne1 = Personne("Alice", 40)
etudiant1 = Etudiant("Bob", 20, "Informatique")
personne1.se_presenter()
etudiant1.se_presenter()
Enoncé 4 :
Créez une classe Vehicule avec :
• Un attribut marque
• Un attribut modele
• Une méthode afficher_infos() qui affiche les détails du véhicule
Ensuite, créez deux sous-classes :
• Voiture avec un attribut supplémentaire nombre_portes
• Moto avec un attribut type_guidon
Ajoutez dans chaque sous-classe une surcharge de afficher_infos() pour in-
clure les attributs spécifiques.
Test du programme :
class Vehicule:
pass
class Voiture(Vehicule):
pass
class Moto(Vehicule):
pass
# Test
v1 = Voiture("Toyota", "Corolla", 4)
m1 = Moto("Yamaha", "MT-07", "sport")
v1.afficher_infos()
m1.afficher_infos()
Exercice 4 : Gestion des utilisateurs système
Objectif : Manipuler des classes et l’encapsulation pour gérer des utilisateurs.
Énoncé 5 :
Créer une classe UtilisateurSysteme avec :
• Un attribut nom_utilisateur.
• Un attribut privé mot_de_passe.
• Une méthode changer_mot_de_passe(nouveau_mdp).
3
• Une méthode afficher_infos() qui affiche le nom d’utilisateur (mais pas
le mot de passe).
Créer une classe Admin qui hérite de UtilisateurSysteme et ajoute :
• Une méthode reinitialiser_mdp(utilisateur), qui remet un mot de
passe par défaut "admin123".
Test du programme :
class UtilisateurSysteme:
def __init__(self, nom_utilisateur, mot_de_passe):
self.nom_utilisateur = nom_utilisateur
self.__mot_de_passe = mot_de_passe # Attribut privé
class Admin(UtilisateurSysteme):
pass
# Test
user1 = UtilisateurSysteme("user1", "pass123")
admin1 = Admin("admin", "securepass")
user1.afficher_infos()
user1.changer_mot_de_passe("newpass456")
admin1.reinitialiser_mdp(user1)
Exercice 3 : Simulation d’un pare-feu
Objectif : Utiliser les classes et la gestion des listes pour filtrer des adresses
IP.
Énoncé 6 :
Créer une classe PareFeu qui :
• Contient une liste adresses_bloquees.
• A une méthode ajouter_ip(ip) pour bloquer une adresse.
• A une méthode supprimer_ip(ip) pour débloquer une adresse.
• A une méthode est_bloquee(ip) qui retourne True si l’adresse est blo-
quée.
Correction :
class PareFeu:
def __init__(self):
self.adresses_bloquees = []
def ajouter_ip(self, ip):
pass
def supprimer_ip(self, ip):
pass
4
def est_bloquee(self, ip):
pass
# Test
firewall = PareFeu()
firewall.ajouter_ip("[Link]")
firewall.ajouter_ip("[Link]")
print(f"[Link] est bloquée ? {firewall.est_bloquee('[Link]')}")
firewall.supprimer_ip("[Link]")
print(f"[Link] est bloquée ? {firewall.est_bloquee('[Link]')}")
Exercices notés
Exercice 1 : Hiérarchie de formes géométriques en POO
Objectif : Créer une hiérarchie de classes pour représenter des formes
géométriques en utilisant les concepts de la programmation orientée objet
(héritage, polymorphisme, abstraction). Implémenter des méthodes de calcul
d’aire et de périmètre, valider les entrées et comparer les formes par leur aire.
Énoncé :
1. Classe de base Forme : - Méthodes abstraites aire() et perimetre(). -
Surcharge de l’opérateur > pour comparer deux formes par leur aire.
2. Sous-classes :
• Cercle : Prend un rayon en paramètre. Valide que le rayon est
positif.
• Rectangle : Prend une longueur et une largeur. Valide que les di-
mensions sont positives.
• Triangle : Prend trois côtés. Valide que les côtés forment un triangle
valide (inégalité triangulaire).
3. Fonctionnalités :
• Calcul de l’aire et du périmètre pour chaque forme.
• Comparaison de deux formes avec > (ex: cercle > rectangle re-
tourne True si l’aire du cercle est plus grande).
Exercice 2
Objectif :
• Modéliser un réseau informatique simplifié avec des classes représentant
des équipements réseau (routeurs, commutateurs, serveurs, clients).
• Implémenter des méthodes pour gérer les connexions, simuler le transfert
de données et calculer des métriques réseau en utilisant la POO (héritage,
polymorphisme, encapsulation).
Énoncé :
1. Classe de base AppareilRéseau
• Attributs :
5
– adresse_ip (string, format valide : “[Link]”, valida-
tion requise).
– bande_passante (en Mbps, valeur positive).
– appareils_connectés (liste d’objets AppareilRéseau).
• Méthodes :
– connecter(appareil) : Ajoute un appareil à appareils_connectés
si la connexion est possible.
– déconnecter(appareil) : Retire un appareil de la liste.
– envoyer_données(données, destination) : Simule l’envoi de
données en vérifiant la bande passante disponible.
– recevoir_données(données) : Affiche un message de réception.
– statistiques() : Retourne le volume total de données en-
voyées/reçues (en Mo).
• Méthode abstraite type_appareil().
2. Sous-classes à implémenter :
• Routeur :
– Peut connecter jusqu’à 8 appareils.
– Redirige les données vers la destination appropriée.
– Surcharge statistiques() pour inclure le nombre de paquets
routés.
• Commutateur :
– Peut connecter jusqu’à 24 appareils.
– Apprend automatiquement les adresses MAC (simulées par
adresse_ip).
• Serveur :
– Bande passante fixe à 1000 Mbps.
– Stocke des fichiers (simulés par un dictionnaire fichiers).
• Client :
– Peut télécharger un fichier depuis un Serveur.
3. Règles :
• Validation des adresses IP avec une expression régulière.
• Un Client ne peut se connecter qu’à un Routeur ou un Commutateur.
• Les données envoyées consomment de la bande passante (1 Mo = 8
Mbps pendant 1 seconde).
6
4. Fonctionnalités avancées :
• Comparer deux appareils avec > pour classer par bande passante
utilisée.
• Simuler une surcharge réseau (si la bande passante est dépassée,
ajouter un délai de 200 ms).
Test du programme :
routeur = Routeur(adresse_ip="[Link]", bande_passante=1000) # Création des appareils
commutateur = Commutateur(adresse_ip="[Link]", bande_passante=100)
serveur = Serveur(adresse_ip="[Link]")
client = Client(adresse_ip="[Link]", bande_passante=100)
# Connexions
[Link](commutateur)
[Link](client)
[Link](serveur) # Doit échouer (connexion directe non autorisée)
# Simulation
serveur.ajouter_fichier(nom="[Link]", taille=500) # 500 Mo
client.télécharger_fichier(serveur, "[Link]")
print([Link]()) # Bande passante utilisée : 4000 Mbps, paquets routés : 1
print(client > commutateur) # True si le client a utilisé plus de bande passante