Upload
others
View
6
Download
0
Embed Size (px)
Citation preview
RAPPELS DE POO
Patrick Bellot
Télécom ParisTech
telecom-paristech.fr
2009
1
2
Programmation Structurée
(N. Wirth)
Programme = Structures de données + Algorithmes
Exemple :
– le type arbre binaire ;
– les parcours préfixé, infixé et postfixé.
3
Complexité du Logiciel
(Exemples)
• comportements répartis :
– programmation en réseaux ;
– robots dans une usine.
• interfaces graphiques :
– difficultés de modélisation ;
– difficultés de programmation.
• très grands logiciels :
– structure du logiciel ;
– partage de code.
4
Une solution : les Objets
(Définitions)
1. Conceptuellement, un objet est la modélisation complète d’une
entité ou d’un concept du problème à traiter :
– les objets co-existent indépendamment ;
– ils communiquent par envois de messages.
2. Techniquement, un objet est une entité regroupant des données,
les attributs, et les algorithmes permettant de manipuler ces
données, les méthodes :
– les objets exécutent les méthodes ;
– une méthode peut modifier l’objet et envoyer des messages.
5
Les interfaces graphiques
(Un exemple significatif)
Champ d’entrée n. 2
Barre de menu Edit
Cut
Copy
Paste
-----
Clear
Champ d’entrée n. 1
Nom
Prénom
Search Quit
Recherche de fiche
Résultats
Bla bla bla
Etc...
Close
6
Les interfaces graphiques
(Un exemple significatif)
Un algorithme capable de gérer tous les événements utilisateurs est
inconcevable. L’idée de la programmation orientée objet est de
modéliser chacun des éléments graphiques de l’interface comme un
objet en soi, ces objets sont capables de communiquer par envoi de
messages.
L’utilisateur de l’interface est également considéré comme un objet : il
envoie les messages initiaux (clic de souris, frappe de clavier) qui
déclenchent l’exécution des méthodes.
7
Les interfaces graphiques
(Un exemple significatif)
– L’utilisateur clique sur le bouton Clear : envoi par le système de fenêtrage du
message activate() au bouton ; celui-ci exécute la méthode correspondante :
– le bouton envoie le message clear() à la fenêtre mère ; celle-ci exécute la
procédure correspondante :
– elle envoie le message clear() au champ d’entrée n. 1 ; celui-ci exécute
la méthode correspondante et renvoie la valeur void quand il a fini ;
– elle envoie le message clear() au champ d’entrée n. 2 ; celui-ci exécute
la méthode correspondante et renvoie la valeur void quand il a fini ;
– elle envoie le message clear() à la fenêtre de résultats ; celle-ci exécute
la méthode correspondante et renvoie la valeur void quand elle a fini ;
– la fenêtre principale renvoie la valeur void au bouton Clear quand elle a
fini.
– le bouton renvoie la valeur void au système de fenêtrage et l’utilisateur
reprend la main.
8
Les interfaces graphiques
(Un exemple significatif)
Champ d’entrée n. 2
Barre de menu Edit
Cut
Copy
Paste
-----
Clear
Champ d’entrée n. 1
Nom
Prénom
Search Quit
Recherche de fiche
Résultats
Bla bla bla
Etc...
Close
Utilisateuractivation()
clear()
clear() voidclear() void
clear()
void
void
void
1
2
3 4 5 6
7
8
9
10
9
Les interfaces graphiques
(Un exemple significatif)
Les avantages :
• l’algorithme est morcelé : chaque objet possède ses propres
méthodes pour répondre aux messages ;
• chaque objet est responsable des interactions avec son
environnement qui est constitué des objets qu’ils connaît ;
• les algorithmes de chaque objet sont plus faciles à concevoir et
plus conçis qu’un algorithme global qui tenterait de tout gérer ;
• si des objets graphiques sont créés dynamiquement alors il suffit
de les créer et de les laisser attendre des messages ; il n’est pas
nécessaire de modifier les algorithmes existants.
10
La classe
La classe remplace le type des autres langages de programmation. Un
objet est décrit par une classe, on dit qu’il appartient à la classe ou
bien encore, qu’il est instance de la classe.
Une classe possède :
– un nom symbolique ;
– des déclarations d’attributs : les attributs sont des données
attachées à l’objet décrit par la classe ; ces attributs peuvent être
d’autres objets (ce sont alors des connaissances) ;
– des déclarations de méthodes : les méthodes sont des procédures
ou des fonctions que l’objet sait exécuter.
11
Un Exemple : la classe Rectangle
class Rectangle {
int xc, yc ; // coordonnées
int lg, ht ; // dimensions
void changer_coordonnées(int nx, int ny) {
// méthode pour déplacer le rectangle
xc = nx ;
yc = ny ;
}
int surface() {
// méthode pour calculer la surface
return lg*ht ;
}
}
12
L’instanciation
Pour exister, un objet doit être créé. Le processus de création est
appelé l’instanciation. Une variable :
Rectangle r ;
est destinée à contenir la référence d’un objet. Initialement, la
variable contient une référence nulle. Pour créer un objet référencé
par la variable r :
r = new Rectangle() ;
13
Instanciation et initialisation
class Rectangle {
int xc, yc ; // coordonnées
int lg, ht ; // dimensions
public Rectangle(int ix, int iy, int il, int ih) {
xc = ix ; // INITIALISATION
yc = iy ;
lg = il ;
ht = ih ;
...
}
14
Instanciation et initialisation
La procédure d’initialisation doit être utilisée :
r = new Rectangle(10,10,50,20) ;
15
L’arbre des instanciations
Classe Rectangle
xc = 0yc = 0lg = 20ht = 10
xc = 50yc = 30lg = 30ht = 5
xc = 5yc = -20lg = 10ht = 5
- déclarations d’attributs- déclarations de méthodes
Classe
Instances
16
L’envoi de message
L’envoi de message est la manière idéalisée de représenter
l’instruction demandant à un objet d’exécuter une méthode :
objet_receveur.méthode(paramètres...)
Ainsi, si l’on désire connaître la surface d’un rectangle référencé par
une variable r :
Rectangle r ;
...
int s = r.surface() ;
...
17
L’envoi de message
L’envoi de message peut être :
• synchrone : l’objet envoyeur envoie un message à l’objet receveur ;
l’objet envoyeur se met en attente ; l’objet receveur exécute la
méthode correspondant au message et renvoie un résultat ;
l’objet envoyeur récupère le résultat et continue son exécution ;
• asynchrone : l’objet envoyeur ne se met pas en attente de la
réponse ; il continue son exécution pendant que l’objet receveur
s’exécute également ; il consultera la réponse plus tard ; on parle
alors d’objets concurrents ou bien d’acteurs.
18
L’héritage
Telle que présentée, la classe ne se différencie guère d’un module ou paquetage, i.e. la
réunion d’un ensemble de déclaration de types, de données, de procédures et de
fonctions. La différence entre classe et module réside essentiellement dans la notion
d’héritage.
Lorsque l’on déclare une classe A, il est possible de déclarer que la classe A, alors
appelée sous-classe, hérite de la classe B appelée la superclasse. Toutes les déclarations
faites dans la classe B sont alors héritée dans la classe A.
Classe B
Relation d’héritage
Classe A
19
L’héritage
Enrichissement & Substitution
Une fois faite la déclaration d’héritage «A hérite de B», il est possible
d’enrichir la classe A par de nouveaux attributs et/ou de nouvelles
méthodes. On parle alors d’enrichissement ou d’extension modulaire.
Parmi les méthodes que A hérite de B, certaines peuvent ne plus
convenir. On peut alors les redéfinir. On parle alors de redéfinition ou
de substitution de méthodes.
Enrichissement et substitution ne sont pas exclusifs.
20
L’héritage — Substitution
class Rectangle {
int lg, ht ; // dimensions
void changer_longueur(int nl) { lg = nl ; }
......
}
class Carré extends Rectangle {
void changer_longueur(int nl) { // REDÉFINIE
lg = nl ;
ht = nl ; // La hauteur doit aussi être changée
}
......
}
21
L’héritage — Enrichissement
class Rectangle {
......
}
class Rectangle_Orienté extends Rectangle {
int Angle ; // orientation du rectangle
......
}
22
L’arbre d’héritage
Rectangle_orienté
Cercle
Figure
Carré
Carré_orienté
Rectangle
23
Héritage simple et multiple
• L’héritage est dit simple si chaque classe hérite au plus d’une
classe : Java, SmallTalk. L’héritage est alors représenté par
un arbre ou une forêt d’arbres.
• L’héritage est dit multiple si chaque classe peut hériter de
plusieurs classes : C++ , Eiffel. L’héritage est alors représenté
par un ou plusieurs graphes orientés.
24
Le graphe d’héritage
Cercle
Rectangle_orienté
Carré_Orienté
Rectangle
Figure
Carré
Figure_orientée
Cercle_coloré
Figure_colorée
Carré_coloré
25
Héritage Multiple et Héritage Simple
L’héritage multiple est bien plus puissant que l’héritage simple. Une
classe d’objet peut être construite par héritages des différentes classes
décrivant ses différentes propriétés.
Exemple. Carré_coloré_orienté hérite :
– de Carré,
– de Figure_colorée
– et de Figure_orientée.
Avec l’héritage simple, on serait obligé de dupliquer le code.
Meilleur partage de code.
26
Héritage Multiple et Héritage Simple
L’héritage multiple est source de conflits qui ne sont pas de la
responsabilité du programmeur.
Exemple. La classe Téléphone_mural hérite de la classe Téléphone et
de la classe Objet_mural. Chacune des deux super-classes peut avoir
une méthode décrocher() !!!
Deux solutions :
1. proposer une procédure de résolution de conflits, i.e. une
procédure de sélection de la méthode, et s’y tenir (C++ ) ;
2. donner au programmeur des outils de résolution de conflits, par
exemple la clause d’adaptation d’héritage d’Eiffel qui permet de
renommer ou d’invalider des méthodes héritées.
27
Méthodes et classes abstraites — Le problème
Rectangle_orienté
Cercle
Figure
Carré
Carré_orienté
Rectangle
Figure table[10] ;
for (int i=0;i<10;i++) table[i].dessiner() ;
La classe Figure ne connaît pas de méthode dessiner(). Cette
méthode n’aurait aucun sens.
28
Méthodes et classes abstraites — La solution
public abstract class Figure { // classe abstraite
public abstract void dessiner() ; // méthode abstraite
....
}
Classe abstraite. Une classe abstraite ne peut pas avoir d’instances
directes.
Méthode abstraite. Déclarée dans une classe abstraite, elle doit être
définie dans toutes les sous-classes concrètes.
29
Méthodes et classes abstraites — Le fonctionnement
Figure table[10] ;
for (int i=0;i<10;i++) table[i].dessiner() ;
– si table[i] est une instance de Carré, appeler la méthode
dessiner() de la classe Carré ;
– si table[i] est une instance de Cercle, appeler la méthode
dessiner() de la classe Cercle ;
– etc.
Recherche dynamique de la méthode.
30
Les mécanismes de protection
Afin de préserver l’intégrité des objets et de renforcer la modularité pour
améliorer la sûreté du code, les langages proposent des mécanismes de
protection concernant l’accessibilité des attributs et des méthodes par
d’autres objets. Cela définit l’interface publique des objets. Exemples :
– accessibilité nulle, en lecture et en écriture des attributs ;
– accessibilité des attributs et des méthodes :
– accessibilité nulle : attributs et méthodes sont privées ;
– accessibilité uniquement par les objets instances des sous-classes ;
– accessibilité uniquement par les objets instances des classes du
même groupe de classes ;
– accessibilité totale.
31
Les mécanismes de protection
Exemples.
• Ainsi, dans l’exemple de l’interface, ce n’est pas le bouton Clear()
qui va effacer lui-même les champs d’entrée dans des attributs.
Il envoie un message aux champs d’entrée qui se chargent
eux-même de s’effacer et d’effectuer des actions complémentaires.
• Dans le cas d’une Figure, changer ses coordonnées implique de la
redessiner. Il ne faut donc pas qu’un autre objet puisse modifier
les coordonnées en oubliant de redessiner. Les attributs xc et yc
ne doivent donc pas être accessible en écriture. Leur modification
doit donc passer par une procédure !
32
Les objets
– des langages de programmation et des cultures ;
– des méthodes de conception et de développement ;
– des environnements de développement ;
– des avancées Génie Logiciel (programmation contractuelle) ;
pour :
– la modélisation des problèmes (interfaces, etc.) ;
– les logiciels complexes (organisation et développement) ;
– la modularité (classe = module) ;
– la réutilisabilité (après héritage) ;
– l’évolutivité (ajouter un type de figure).
33
Un exemple
Les expressions et leur évaluation
Une expression est :
– soit une constante entière ;
– soit une opération (+,*,etc.) appliquée à deux expressions.
D’où une classe Expression qui va être dérivée en deux sous-classes
Constante et Opération.
OpérationConstante
Expression (a)
34
Les expressions et leur évaluation
public abstract class Expression {
// classe abstraite car il n’y aura pas d’instance directe
public abstract int évaluer() ;
}
public class Constante extends Expression {
private int valeur ; // attribut privé
public Constante(int v) { valeur = v ; }
public int évaluer() { return valeur ; }
}
35
Les expressions et leur évaluation
Une erreur !
public class Opération extends Expression {
protected Expression og, od ;
protected char op ;
public int évaluer() {
switch (op) {
case ’+’ : return og.évaluer() + od.évaluer() ;
case ’*’ : return og.évaluer() * od.évaluer() ;
....
....
}
Code complexe et pour toute nouvelle opération : modifier le code
existant !
36
Les expressions et leur évaluation
Le corrigé !
public abstract class Opération extends Expression {
protected Expression og, od ;
public Opération(Expression g, Expression d) {
og = g ; // initialisation
od = d ;
}
}
37
Les expressions et leur évaluation
Le corrigé !
38
public class Addition extends Expression {
public Addition(Expression g, Expression d) {
super(g,d) ; // initialisation de la classe mère
}
public int évaluer() {
return og.évaluer() + od.évaluer() ;
}
}
39
Les expressions et leur évaluation
Le corrigé !
40
public class Soustraction extends Expression {
public Soustraction(Expression g, Expression d) {
super(g,d) ; // initialisation
}
public int évaluer() {
return og.évaluer() - od.évaluer() ;
}
}
41
Les expressions et leur évaluation
Opération (a)Constante
Expression (a)
Addition SoustractionProduit
Intérêts
– le code est moins complexe, les méthodes plus petites ;
– le code est extensible sans modification.
42
Un message
La syntaxe et quelques principes ne sont pas suffisants pour réaliser
une bonne modélisation orientée objet.
On ne s’improvise pas programmeur orienté-objet. L’apprentissage
des objets est long.
Il ne faut pas sous-estimer l’apprentissage et s’enfermer dans une
attitude de « je connais et je l’ai déjà vu ! ».
La culture objet est remplie de notions spécifiques d’algorithmiques
et de problèmes réputés insolubles. Ne pas les connaître, c’est
s’exposer à de ridicules déconvenues.