Abstraction
Progression
#Abstraction
L’abstraction simplifie des systèmes complexes en cachant les détails non essentiels pour se concentrer sur l’intention et les interfaces.
#Qu’est‑ce que l’abstraction ?
L’abstraction sépare le « quoi » (l’idée ou la spécification) du « comment » (l’implémentation concrète). Elle réduit la complexité, permet de raisonner sur un comportement attendu et autorise plusieurs implémentations possibles derrière la même interface.
#Niveaux d’abstraction
Les données sont décrites par des types et des structures (float
, listes chaînées, dictionnaires) qui fixent ce que l’on peut faire sans exposer la représentation interne.
Les procédures regroupent des fonctions ou des méthodes dont on retient le contrat (sort
, append
, send
). L’algorithme exact peut changer tant que le contrat reste vrai.
Le contrôle englobe les patrons (boucles, itérateurs, map/reduce, futures) qui expriment l’intention de parcours, de transformation ou d’orchestration sans détailler la mécanique.
#Exemples rapides
Un set
assure l’unicité et permet de tester l’appartenance en temps quasi constant sans révéler qu’il repose sur une table de hachage. L’appel à liste.sort()
se contente de promettre un ordre croissant ; la bibliothèque choisit l’algorithme le plus adapté. Lorsque l’on écrit for x in it
, on consomme un itérateur étape par étape sans manipuler les pointeurs ni l’état interne.
Un ADT spécifie des opérations (ex: pile: push/pop/peek
) et des propriétés
(LIFO) sans imposer l’implémentation (tableau, liste chaînée…).
#Interfaces et invariants
Une interface définit un contrat : des préconditions, des postconditions et parfois des invariants (ex: pile toujours LIFO). Tant que le contrat reste vrai, l’implémentation peut évoluer. L’encapsulation garde les détails internes privés pour éviter que le code appelant ne dépende de choix susceptibles de changer.
1class Stack:2 def __init__(self):3 self._a = [] # détail interne4 def push(self, x):5 self._a.append(x)6 def pop(self):7 if not self._a:8 raise IndexError('empty')9 return self._a.pop()
#Abstraction et composition
Les systèmes s’assemblent par couches successives : matériel → système d’exploitation → runtime → bibliothèque → application. Chaque palier expose un langage plus expressif que le précédent. La loi de Déméter rappelle de limiter les dépendances transverses : on discute avec ses voisins directs, pas avec toute la chaîne interne.
#Exercices
- Concevoir l’ADT
Queue
(file) en listant les opérations autorisées, les pré/post-conditions, puis en proposant deux implémentations (tableau, liste chaînée). - Définir une interface
Repository<T>
avec les opérations CRUD et écrire une version en mémoire puis une version persistant en fichier. - Reprendre une boucle
for
et la réécrire avecmap
/filter
pour illustrer la montée en abstraction sur le contrôle.