analyse merise sql
DESCRIPTION
MERISETRANSCRIPT
-
Analyse pour le BTS IG/SIO
Alexandre Mesle
1er novembre 2014
-
Table des matie`res
1 Merise 3
1.1 Introduction . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . 31.1.1 Pourquoi lanalyse ? . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . 31.1.2 Comment ca marche ? . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . 31.1.3 Logiciels . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . 3
1.2 Dictionnaire des donnees . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . 41.2.1 Crite`res de selection des donnees . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . 41.2.2 Donnees a` ajouter au dictionnaire . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . 4
1.3 Dependances fonctionnelles . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . 51.3.1 Definition . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . 51.3.2 Quelques re`gles . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . 51.3.3 Dependances fonctionnelles faibles . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . 6
1.4 Mode`le conceptuel des donnees . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . 71.4.1 Exemple introductif . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . 71.4.2 Les entites . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . 71.4.3 Les Associations . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . 71.4.4 Les Cardinalites . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . 81.4.5 Associations et attributs . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . 81.4.6 Associations complexes . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . 9
1.5 Mode`le physique des donnees . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . 121.5.1 Introduction . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . 121.5.2 Formalisme . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . 121.5.3 Calcul du MPD . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . 12
1.6 Exercices Recapitulatifs . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . 14
2 UML 15
2.1 Introduction au UML . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . 152.1.1 Classes . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . 152.1.2 Relations . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . 162.1.3 Heritage . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . 182.1.4 Relations specifiques . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . 182.1.5 Exercices . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . 21
2.2 Design patterns (En construction) . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . 222.2.1 Factory . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . 222.2.2 Singleton . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . 222.2.3 Wrapper . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . 232.2.4 Adapter . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . 242.2.5 Strategy . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . 242.2.6 Iterator . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . 252.2.7 Observer . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . 272.2.8 Proxy . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . 282.2.9 Decorator . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . 28
1
-
A Quelques Corriges 30
A.1 Dependances fonctionnelles . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . 30A.2 MCD . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . 30A.3 UML . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . 31A.4 Design patterns . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . 34
A.4.1 Factory . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . 34A.4.2 Singleton . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . 34A.4.3 Wrapper . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . 35A.4.4 Strategy . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . 38A.4.5 Iterateur . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . 39A.4.6 Observer . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . 42A.4.7 Proxy . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . 43A.4.8 Decorator . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . 44
2
-
Chapitre 1
Merise
1.1 Introduction
1.1.1 Pourquoi lanalyse ?
Ce cours portera essentiellement sur la branche de lanalyse permettant la modelisation de bases de donneesrelationnelles. Les SGBDR (serveurs de bases de donnees relationnelles) sont des logiciels stockant des donnees dansdes tables.
Les tables sont des tableaux a` deux dimensions. Les donnees sont reparties dans ces tables dune facon permettantde modeliser des situations plus ou moins complexes. Lanalyse est une phase se trouvant en amont, et permettant dedeterminer de quelle facon agencer les tables pour que les donnees representent au mieux la realite.
De facon tre`s generale, analyser signifie comprendre un objet en le decomposant en ses constituants. Ce qui setranspose aux bases de donnees en decomposant une situation reelle en donnees, tout en observant de quelle faconelles sont assemblees pour les modeliser au mieux a` laide de tables.
1.1.2 Comment ca marche ?
Il existe plusieurs methodes. La plus connue est la methode Merise. Il sagit dun ensemble de techniques mathematiquesayant pour but de modeliser une situation a` laide de shemas. Les trois premie`res etapes sont :
DDD, le dictionnaire des donnees est lensemble des donnees qui seront representees dans la base. DF, les dependances fonctionnelles sont des relations entre les donnees. MCD, le modele conceptuel des donnees, ou mode`le entites-associations est un graphe faisant la synthe`se de la
situation. Le MCD est un mode`le tre`s puissant, il est dense et exprime une tre`s grande quantite dinformations.Une fois ces trois etapes achevees, il existe une technique permettant den deduire le MPD (mode`le physique des
donnees). Le MPD donne directemment larchitecture de la base de donnees.
1.1.3 Logiciels
Merise
Le logiciel JMerise permet de representer des MCDs et de les exporter vers une base de donnees. Je vous conseilledapprendre a` vous en servir.
Les shema dans ce cours sont realises a` laide de Mocodo.
UML
Le plugin pour eclipse objectaid gene`re un diagramme UML a` partir dun projet Java. Pour inclure des illustrations,UmlGraph presente lavantage de generer de de nombreux formats a` partir dun fichier de classes java et de gerer luimeme le placement.
Limpossibilite de faire des classes-associations ou des relations ternaires a necessite lemploi de Tikz-Uml pour laredaction de ce document.
3
-
0,N 1,1
PASSER
1,N 0,N
COMPORTER
quantit
PRODUIT
numprod
nomprod
prixprod
CLIENT
numcli
nomcli
COMMANDE
numcom
datecom
Figure 1.1 Exemple Mocodo
Client ~ num : int ~ nom : String ~ Client()
Commande ~ num : int ~ nom : String ~ Commande()
0..*
1
Comporter ~ quantite : int ~ Comporter()
1..*
0..*
Produit
~ num : int ~ nom : String ~ prix : int ~ Produit()
0..*
1
Figure 1.2 Exemple UmlGraph
1.2 Dictionnaire des donnees
1.2.1 Crite`res de selection des donnees
Les donnees doivent etre : Sans redondance Atomiques
1.2.2 Donnees a` ajouter au dictionnaire
Il est usuel dajouter au dictionnaire des donnees, numeriques, appelees identifiants. Par exemple si vous devezmodeliser une liste de clients, il serait malvenu de ne disposer que de leurs noms et prenoms. En effet, tout doublondans ces donnees serait une source derreurs. Il convient donc dajouter un numero de client (numCli par exemple)pour que chaque client soit identifie de facon unique.
Exercice 1 - Secretariat pedagogique
Nous souhaitons gerer un secretariat pedagogique. Nous recensons les etudiants en utilisant leurs noms, prenoms etadresse. Des formations sont organisees en modules, qui eux-memes sont repartis sur des semestres, et chaque etudiantest affecte a` une formation. On tiendra compte du fait quun etudiant peut redoubler ou suspendre sa formation enprenant des conges. Constituer le dictionnaire des donnees permettant de modeliser la situation ci-dessus.
4
-
-client
*
-produits1
*
Client
- num : int- nom : String- prenom : String
+ getNum() : int+ getNom() : String+ getPrenom() : String
Commande
- num : int- date : Date
+ getNum() : int+ getDate() : Date
Produit
- num : int- nom : String- prix : int
+ getNum() : int+ getNom() : String+ getPrix() : int
Comporter
-quantite : int
+getQuantite() : int
Figure 1.3 Exemple Tikz-Uml
1.3 Dependances fonctionnelles
1.3.1 Definition
Deux donnees A et B sont en dependance fonctionnelle si la connaissance dune valeur de A determine la connais-sance dau plus une valeur de B.
Par exemple, la connaissance dun numero de securite sociale determine un seul nom de famille, celui du titulairede ce numero. Par contre, un prenom ne determine rien, car plusieurs personnes peuvent avoir le meme prenom. Onpeut representer cette DF de la facon suivante :
numSecu nomPers
Il est aussi possible que la donnee A soit composee de plusieurs donnees. Par exemple, si lon souhaite connatrela note obtenue par un etudiant a` un examen, il est necessaire de connatre le numero de letudiant, le numero dumodule, et la session quil passait. Ce qui se represente :
numEtudiant, numModule, numSession valeurNote
1.3.2 Quelques re`gles
Identifiants
Si on a une dependance A B, A est necessairement un identifiant. En effet, toute donnee netant pas un identifiantest ambigue, par consequent, il est impossible de sen servir pour etablir des re`gles de dependance.
Arcs de transitivite
Si on a A B C, il est inutile dindiquer sur le diagramme que A C, cette relation napporte aucuneinformation supplementaire.
5
-
1.3.3 Dependances fonctionnelles faibles
Une dependance fonctionnelle de A vers B est dite faible si la connaissance dune valeur de A permet de determiner0 ou 1 valeur de B. Dans ce cas on represente la fle`che en pointilles.
Une DF classique, par opposition a` une DF faible, est dite forte.
Exercice 1 - Secretariat pedagogique
Nous souhaitons gerer un secretariat pedagogique. Nous recensons les etudiants en utilisant leurs noms, prenomset adresse. Des formations sont organisees en modules, qui eux-memes sont repartis sur des semestres. Un etudiant nepeut etre inscrit que dans une formation a` la fois, et un module est affecte a` un seul semestre dans une formation. Ontiendra compte du fait quun etudiant peut redoubler ou suspendre sa formation en prenant des conges. Representezle graphe des dependances fonctionnelles associees a` cette situation.
Exercice 2 - Chane dapprovisionnement
Nous souhaitons gerer une chane dapprovisionnement. Nous tenons une liste de produits et une liste de fournis-seurs. Certains produits peuvent etre proposes par plusieurs fournisseurs, a` des prix qui peuvent etre differents. Nousgarderons lhistorique des livraisons en memoire, avec pour chacune dentre elle la date de livraison ainsi que le detaildes produits livres. Construire le graphe des DF modelisant cette situation.
6
-
1.4 Mode`le conceptuel des donnees
Pour le moment, en analyse, nous avons vu comment decomposer une situation reelle en donnees, et nous avonsvu aussi comment representer des liaisons entre ces donnees. Cependant, le graphe des dependances fonctionnelles estincomplet dans le sens ou` il ne permet pas de representer suffisamment de liaisons pour representer fide`lement la realite.
Le MCD, dit aussi Mode`le Conceptuel des Donnees, est une representation graphique davantage comple`te quele graphe des dependances fonctionnelles. Lelaboration dun MCD necessite plus dobservations de la situation que legraphe des DF. Le mode`le est par consequent suffisamment complet pour quil soit possible de deduire la repartitiondes donnees dans les tables sans observation supplementaire de la situation. Cette etape est donc la dernie`re etapeepineuse dune analyse.
Commencons par examiner un exemple.
1.4.1 Exemple introductif
Le bureau des etudiants souhaite lorsquil planifie des soirees, lister les etudiants qui ont reserve des places pourgerer la billetterie. Nous utiliserons les donnees suivantes :
numetud nometud prenomnometud mailetud numsoiree nomsoiree datesoireeIl apparat clairement que : numetud nometud numetud prenometud numetud mailetud numsoiree nomsoiree numsoiree datesoireeOn observe que les dates des soirees ne peuvent pas servir didentifiant parce que plusieurs soirees peuvent etre
programmees le meme soir par le BDE. On remarque aussi que les donnees numetud, nometud, prenomnometud etmailetud sont liees, parce que trois dentre elles dependent de numetud. De meme, on peut regrouper numsoiree,nomsoiree et datesoiree.
A titre de parenthe`se, rappelons que numetud 6 numsoiree parce quun etudiant peut avoir reserve des placespour plusieurs soirees (ou aucune). De facon analogue, on a numsoiree 6 numetud, parce quil peut y avoir plusieursetudiants dans une soiree, tout comme il peut ny en avoir aucun. On conclura donc que le graphe des DF ne permetpas de representer la facon comple`te la billetterie, vu quil ne permet pas de mettre en correspondance les etudiantset les soirees.
1.4.2 Les entites
Il est usuel, en analyse, de regrouper dans des entites des donnees liees a` leur identifiant par une relation dedependance fonctionnelle. On represente cela ainsi :
Les botes dans lesquelles les donnees sont regroupees sont des entites, les identifants doivent etre soulignes, ettoutes les donnees doivent etre en dependance fonctionnelle avec lidentifiant.
La cle dessinee a` cote de lidentifiant est ajoutee par Open Model Sphere, vous navez pas besoin de la dessiner.Par rapport a` la question que nous nous posions, et qui etait comment representer graphiquement les correspondancesentre les soirees et les etudiants, nous navons toujours pas repondu.
1.4.3 Les Associations
Les associations sont des correspondances entre les entites, on les represente ainsi :
7
-
ETUDIANT
numetud
nometud
prenometud
mailetud
SOIREE
numsoiree
nomsoiree
datesoiree
Figure 1.4 Exemple entites
_,_ _,_
PARTICIPER
ETUDIANT
numetud
nometud
prenometud
mailetud
SOIREE
numsoiree
nomsoiree
datesoiree
Figure 1.5 Exemple associations
Le fait que Etudiant soit associe a` Soiree signifie que la base de donnees devra permettre etant donne un etudiantparticulier, de savoir a` quelle(s) soiree(s) il a participe, et vice-versa, a` partir dune soiree donnee, il devra etre possiblede determiner quels etudiants ont participe.
Il est usuel de choisir des verbes pour les nommer, pour la simple raison que la plupart du temps, les entitesrepresentent des objets (au sens tre`s large du terme), et les associations des actions impliquant ces objets.
1.4.4 Les Cardinalites
Etendons notre mode`le : supposons que le BDE souhaite aussi gerer les lieux reserves pour les soirees. Il seraitenvisageable dagrandir notre MCD de la sorte :
_,_ _,_
PARTICIPER
_,_ _,_
SE DEROULERLIEU
numLieu
nomLieu
ETUDIANT
numetud
nometud
prenometud
mailetud
SOIREE
numsoiree
nomsoiree
datesoiree
Figure 1.6 Exemple incomplet...
Le proble`me qui se pose est que ce mode`le est incomplet... En effet la relation Reserver nest du tout de la memenature que la relation Participer... Pourquoi ? Parce que pour une soiree on ne reserve quune salle a` la fois ! On senconvainc en remarquant quil y a une dependance fonctionnelle entre numsoiree et numlieu.
Etant donnee une soiree particulie`re, on lui associe un et un seul lieu, alors qua` un lieu correspond un nombrede soirees inconnu a` lavance. On comple`te le mode`le en ajoutant ce que lon appelle des cardinalites :
Le 0, n entre Etudiant et Participer signifie qua` un etudiant sera associe un nombre de soirees pouvant varierde 0 a` plusieurs. Le n signifie que le nombre de soirees peut etre aussi grand que lon veut. Le 0, 1 separant Soiree deReserver signifie qua` une soiree est associe 0 ou 1 salle. A votre avis, que signifie les autres cardinalites ?
1.4.5 Associations et attributs
Supposons que les etudiants aient le droit de venir avec des personnes exterieures, cest-a`-dire quils aient le droitde reserver plusieurs places. Ou` mettre la donnee nbPlaces ? On ne peut pas la mettre dans Etudiant, ni dans Soiree,
8
-
0,N 0,N
AR
0 1
SE DEROULERLIEU
numLieu
nomLieu
ETUDIANT
numetud
nometud
prenometud
mailetud
SOIREE
numsoiree
nomsoiree
datesoiree
Figure 1.7 Exemple cardinalites
parce que le nombre de place reservees par un etudiant a` une soiree depend a` la fois de la soiree et de letudiant. Lasolution est la suivante :
0,N 0,N
AR
SE DEROULERLIEU
numLieu
nomLieu
ETUDIANT
numetud
nometud
prenometud
mailetud
SOIREE
numsoiree
nomsoiree
datesoiree
Figure 1.8 Exemple attribut
Cet attribut de lassociation Participer signifie qua` chaque fois dun etudiant annoncera sa participation pourune soiree, il devra preciser combien de places il souhaite reserver.
Exercice 1 - Chane dapprovisionnement
Nous souhaitons gerer une chane dapprovisionnement. Nous tenons une liste de produits et une liste de fournis-seurs. Certains produits peuvent etre proposes par plusieurs fournisseurs, a` des prix qui peuvent etre differents. Nousgarderons lhistorique des livraisons en memoire, avec pour chacune dentre elle, le fournisseur qui la effectue, la datede livraison ainsi que le detail des produits livres. Construire un MCD modelisant cette situation.
1.4.6 Associations complexes
Il est possible dexprimer avec des associations des situations relativement elaborees. Des bases donnees complexescomme par exemple celles que lon peut trouver dans des reseaux sociaux se modelisent de facon surprenante.
Reflexives
Si lon souhaite par exemple representer une liste dinternautes pouvant etant etre amis entre eux. Lassociation Etreami met donc un Internaute avec un autre Internaute. Il faut donc pour representer cela utiliser une associationreflexive.
0,N
0,N
ETREINTERNAUTE
numInternaute
Figure 1.9 Exemple reflexive
9
-
Multiples
Un autre cas qui pourrait se presenter est celui ou` il existe de multiples associations entre deux entites. Par exempledans le cas dun groupe (ou forum), il existe pour chaque groupe un internaute particulier qui en est le createur. Cela nedoit pas empecher dautres internautes de sinscrire sur le groupe. On represente cette situation avec deux associationsdifferentes entre ces deux entites.
0,N
E
0,N
CREER
GROUPE
numGroupe
nomGroupe
INTERNAUTE
numInternaute
...
Figure 1.10 Exemple multiple
Ternaires
Il est aussi frequent que plus deux associations soient impliquees dans une association. Si par exemple, on souhaitegarder en memoire les photos partages par internautes sur des groupes, lassociation mettant en relation la photo, lapersonne qui la partage, et le groupe sur lequel elle a ete partagee devra donc relier trois entites.
0,N 0,N
0,N
PARTAGER
GROUPE
numGroupe
nomGroupe
...
INTERNAUTE
numInternaute
...
O
...
Figure 1.11 Exemple ternaire
On remarque au passage que le commentaire depend a` la fois du groupe de linternaute et de la photo.
Exercice 2 - Secretariat pedagogique
Nous souhaitons gerer un secretariat pedagogique. Nous recensons les etudiants en utilisant leurs noms, prenomset adresse. Des formations sont organisees en modules, qui eux-memes sont repartis sur des semestres. Un etudiant nepeut etre inscrit que dans une formation a` la fois, et un module est affecte a` un seul semestre dans une formation. Ontiendra compte du fait quun etudiant peut redoubler ou suspendre sa formation en prenant des conges. Representezun MCD associe a` cette situation.
10
-
Exercice 3 - Arbre genealogique
Nous souhaitons mettre au point un logiciel permettant de representer un arbre genealogique. Cest a` dire listagedes personnes, mariages et filiation. Nous tiendrons compte le fait que les parents peuvent etre inconnus. Par contre,nous ne gererons que les mariages heterosexuels et nous ferons abstractions de certains pratiques en vogue comme latransexualite (si vous etes sages nous ferons un TP la`-dessus plus tard dans lannee). Representez cette situation avecun MCD.
Exercice 4 - CMS
Nous voulons gerer un CMS (content management system). Un CMS est un logiciel permettant de gerer le contenudun ou plusieurs sites web. Chaque site porte un nom, est caracterise par une URL, et est decoupe en categories,imbricables les unes dans les autres. Des utilisateurs sont repertories dans le CMS, et chacun peut avoir le droit (ounon) decrire dans un site web. Chaque utilisateur doit avoir la possibilite de publier des articles dans une categorie dunsite web (pourvu quil dispose de droits suffisants dessus). Un article, en plus de son titre et de son texte dintroduction,est constitue de chapitres portant chacun un nom et contenant un texte. Il va de soi quon doit avoir la possibilitepour chaque site de conserver lhistorique de quel article a ete publie par quel utilisateur. Realisez un MCD adapte a`cette situation.
11
-
1.5 Mode`le physique des donnees
1.5.1 Introduction
Le MPD (Mode`le physique des donnees) est la dernie`re etape de lanalyse. Le MPD nest autre quune liste detables avec pour chacune delle les colonnes faisant partie de cette table. Il sobtient par calcul a` partir du MCD.
1.5.2 Formalisme
Chaque nom de table est suivi dune liste de colonnes entre parenthe`ses. Les cles primaires sont soulignees les cles etrange`res sont precedees par un die`se.
1.5.3 Calcul du MPD
Entites
Une entite devient une table, tous ses attributs deviennent des colonnes et son identifiant devient la cle primaire.
Associations Plusieurs a` plusieurs
Une association aux cardinalites de type . . . , n des deux cotes (donc de type plusieurs a` plusieurs), devient aussiune table :
Les attributs de cette association deviennent des colonnes. Les cles primaires des tables se trouvant de part et dautres de lassociation sont importees sous forme de cles
etrange`res. La concatenation de ces cles etrange`res devient la cle primaire.
_,N _,N
AssociationT
AttributT
EntitA
idA
AttributA
EntitB
idB
AttributB
EntiteA(idA, AttributA) EntiteB(idB, AttributB)
AttributT(#idA, #idB, AttributT)
Figure 1.12 Relations plusieurs a` plusieurs
Dans lexemple ci-dessus, EntiteA et EntiteB sont reliees par AssociationT , leurs cles primaires pA et pB sontdupliquees dans la table AssociationT pour devenir des cles etrange`res. Le couple (p1, pB) devient alors cle primairede AssociationT .
Associations Un a` plusieurs
Une association aux cardinalites de type . . . , 1 dun cote et . . . , n de lautre, (donc de type un a` plusieurs), disparat : La cle primaire de la table se trouvant du cote plusieurs est dupliquee du cote un. Elle devient une cle etrange`re. Les attributs de cette association sont reportes dans la table se trouvant du cote un.Dans cet exemple, AssociationT disparat. La cle primaire de EntiteB, se trouvant du cote plusieurs, est reportee
dans la table EntiteA sous forme de cle etrange`re. AttributT est lui aussi reporte dans la table EntiteA.
Exercice 1 - Livraisons
Construire le MPD pour le cas Livraisons.
12
-
_,1 _,N
AssociationTEntitA
idA
AttributA
EntitB
idB
AttributB
EntiteB(idB, AttributB)EntiteA(idA, AttributA, #idB)
Figure 1.13 Relations un a` plusieurs
Exercice 2 - Secretariat pedagogique
Construire le MPD pour le cas Secretariat pedagogique.
13
-
1.6 Exercices Recapitulatifs
Exercice 1 - Bibliothe`que
Nous souhaitons gerer une bibliothe`que simple. La base de donnees devra recenser une liste douvrages, avec pourchacun le titre et lauteur (eventuellement plusieurs). Vous tiendrez compte du fait que des ouvrages peuvent existeren plusieurs exemplaires, certains pouvant ne pas etre disponibles pour le pret (consultables uniquement sur place, oudetruits). Une liste dadherents devra etre tenue a` jour, les adhesions devant se renouveler une fois par an. Il devraetre possible de verifier quune adhesion est a` jour (cest-a`-dire quelle a ete renouvelee il y a moins dun an), mais ilne sera pas necessaire de connatre lhistorique des renouvellements. Les adherents peuvent emprunter jusqua` 5 livressimultanement et chaque livre emprunte doit etre retourne dans les deux semaines. On devra conserver un historiquepermettant de savoir quel abonne a emprunte quels livres, les dates demprunts et de retours.
1. Realiser une analyse comple`te : DDD, DF, MCD.
2. Determiner le MPD et ecrire le script de creation de tables.
3. Inserer des donnees coherentes dans vos tables.
4. Mettre en place des vues permettant de dobtenir les informations suivantes :
(a) Abonnes dont labonnement nest plus a` jour.
(b) Ouvrages en circulation.
(c) Ouvrages devant deja` etre revenus, et les abonnes correspondants.
(d) Ouvrages disponibles pour le pret.
(e) Ouvrages dont il nexiste plus dexemplaire.
(f) Ouvrages dont tous les exemplaires sont en circulation.
(g) Nombre demprunts par ouvrage.
(h) Abonnes pouvant emprunter (abonnement a` jour et limite non depassee).
(i) Dautres requetes qui vous sembleraient interessantes...
(j) Nombre douvrages en circulation par abonne.
14
-
Chapitre 2
UML
2.1 Introduction au UML
UML est un ensemble de representations graphiques permettant de modeliser des applications utilisant des lan-gages a` objet. Dans ce cours nous nous concentrerons sur les diagrammes de classes. Le diagramme de classe estladaptation du MCD aux classes, cest-a`-dire une representation permettant de rapidement comprendre larchitecturedune application. Son emploi est incontournable de`s que lon aborde des projets dune certaine ampleur.
Pour lire ce document, il est necessaire davoir quelques bases de Merise (premie`re partie de ce cours) et de connatreles grands principes de la programmation objet (classe, instances, heritage, interfaces, etc.).
2.1.1 Classes
Une classe est representee par une bote contenant trois sections : Lentete contient le nom de la classe et certaines informations complementaires (abstraite, interface, etc.). Les attributs sont les variables de classe (static) ainsi que les variables dinstance (non static). Les methodes contiennent les sous-programmes dinstance et de classe.
Point
abscisse : doubleordonnee : double
getAbscisse() : doublegetOrdonnee() : doublesetAbscisse(double)setOrdonnee(double)
Lexemple ci-dessus nous montre une classe Point disposant de deux attributs abscisse et ordonnee, tous deuxde type double. Les quatre methodes (les getter et les setter) se trouvent dans la troisie`me partie de la bote.
Visibilite
La visibilite dun identificateur est notee en le faisant preceder dun symbole + (public) ou - (private), #(protected) ou ~ (package).
Un attribut est : public sil est possible de lutiliser depuis nimporte ou` dans le code. prive sil nest visible que depuis linterieur de la classe. On omet souvent les attributs prive dans le diagramme
de classe. protected sil nest visible que depuis les sous-classes. Attention, en Java un attribut protected nest accessible
que sur lobjet this, vous ne pourrez pas vous en servir sur un autre objet de la meme classe. package, la visibilite par defaut, sil nest visible que dans le package.
15
-
Point
- abscisse : double- ordonnee : double
+ getAbscisse() : double+ getOrdonnee() : double+ setAbscisse(double)+ setOrdonnee(double)
Par exemple dans la classe Point ci-avant abscisse et ordonnee sont prives tandis que les quatre methodes sontpubliques.
Attention : Avec le logiciel que jutilise, les attributs et methodes statiques son soulignes.
2.1.2 Relations
Lorsque deux classes sont reliees par une fle`che, cela signifie que chaque instance de la classe se trouvant a` lextremiteinitiale de la classe contient une reference vers une (ou plusieurs) instances de la classe se trouvant a` lextremite finalede la fle`che. Donc si fle`che part de la classe A vers la classe B, on dit quil y a une relation de A vers B.
Etudiant
- num : int- nom : String- prenom : String
+ getNum() : int+ getNom() : String+ getPrenom() : String
Soiree
- num : int- nom : String- date : Date
+ getNum() : int+ getNom() : String+ getPrenom() : String
Cet exemple modelise linscription detudiants a` des soirees. Un etudiant sera en correspondance avec les soireesauxquelles il est inscrit.
Attribut
Lattribut de la classe situee a` lextremite initiale de la fle`che servant a` representer la relation est tre`s souventprecise a` cote de la fle`che afin dindiquer comment cette relation est implementee. Pour eviter les redondances, on nela precise pas avec les attributs de la classe.
-soirees
Etudiant
- num : int- nom : String- prenom : String
+ getNum() : int+ getNom() : String+ getPrenom() : String
Soiree
- num : int- nom : String- date : Date
+ getNum() : int+ getNom() : String+ getPrenom() : String
Par exemple, memoriser pour un etudiant lensemble des soirees auxquelles il est inscrit necessite une variable(non-scalaire) appelee ici soirees.
Sens de navigation
Vous noterez que les sens des fle`ches indiquent un sens de navigation entre les objets. Si lon a A B, cela signifiequil est possible depuis un objet A de determiner directement lobjet B qui est en relation avec. Vous noterez que lanavigation dans lautre sens ne sera pas facilite par cette specification.
Labsence de fle`che signifie que la navigation peut seffectuer dans les deux sens. Cela peut etre tout a` fait pratiquepour exploiter les classes, mais ce type de reference croisee peut etre assez difficile a` programmer.
16
-
-soirees -etudiants
Etudiant
- num : int- nom : String- prenom : String
+ getNum() : int+ getNom() : String+ getPrenom() : String
Soiree
- num : int- nom : String- date : Date
+ getNum() : int+ getNom() : String+ getDate() : Date
La relation est ici bidirectionnelle, il est possible a` partir dun etudiant de retrouver les soirees et a` partir dessoirees de retrouver un etudiant.
Label
Une relation peut etre accompagnee dun label etiquetant la nature de la relation, ce qui est apprecie lorsque cettedernie`re nest pas evidente.
-soirees -etudiants
Etudiant
- num : int- nom : String- prenom : String
+ getNum() : int+ getNom() : String+ getPrenom() : String
Soiree
- num : int- nom : String- date : Date
+ getNum() : int+ getNom() : String+ getPrenom() : String
InscriptionInscription
Multiplicite
Les valeurs aux extremites des fle`ches sont lanalogue des cardinalites en Merise. Sauf quelles sont a` lenvers !Vous remarquerez aussi que les notations peuvent etre tre`s heteroge`nes : Certaines sont de la forme inf..sup, ou` inf est le plus petit nombre dinstances referencees, et sup le nombre
maximal. Une valeur arbitrairement grande est notee . Tandis que dautres nindiquent quune seule valeur. 1 sil y a un objet reference, sil peut y en avoir 0, 1 ou
plusieurs.
-soirees
*
-etudiants
*
-lieu
* 0..1
Etudiant
- num : int- nom : String- prenom : String
+ getNum() : int+ getNom() : String+ getPrenom() : String
Soiree
- num : int- nom : String- date : Date
+ getNum() : int+ getNom() : String+ getDate() : Date
Lieu
- num : int- nom : String
+ getNum() : int+ getNom() : String
Se deroulerSe derouler
Un etudiant peut sinscrire a` 0, une ou plusieurs soirees, tout comme a` une soirees peut sinscrire un nombrearbitraire detudiants. Par contre, une soiree ne peut se derouler que dans un seul lieu, Le 0 signifiant quon se garde
17
-
le droit de representer des soirees dont le lieu na pas encore ete determine. On notera que plusieurs soirees peuventse derouler dans le meme lieu.
2.1.3 Heritage
Lheritage est note avec une fle`che (quelques fois en pointillees) terminee par un triangle vide. La classe me`repeut etre une classe conventionnelle, une classe abstraite, ou encore une interface. On precise dans ce cas la nature dela classe me`re afin deviter toute confusion. On prete aussi attention au fait que dans certains langages a` objets, enparticulier Java, lheritage multiple est interdit.
Le cas particulier dheritage quest limplementation se represente avec des fle`ches en pointilles.
rtr rtr
q
r
Un objet de type Girafe sera aussi de type Equide, de type Vertebre et enfin de type Animal.Attention : Avec le logiciel que jutilise, les classes et methodes abstraites sont representes en italique.
2.1.4 Relations specifiques
Composition
La composition est la notation utilisee pour transposer les entites faibles ou mondes objets. Une classe A estagregee a` une classe B si toute instance de A est reliee a` une (et exactement une) instance de B, et ne peut donc pasexister sans cette instance de B. La composition implique quune instance de A sera toujours en relation avec la memela instance de B. On la note avec un losange noir du cote de la classe proprietaire.
-client
*
Client
- num : int- nom : String- prenom : String
+ getNum() : int+ getNom() : String+ getPrenom() : String
Commande
- num : int- date : Date
+ getNum() : int+ getDate() : Date
Une commande sans client nexiste pas, la destruction du client entrane la destruction de toutes ses commandes.Une fois cree, une commande sera toujours associee au meme client.
18
-
Agregation
Une classe A est lagregation dune classe B lorsquune instance de A est une collection dinstances de B. On larepresente avec un losange blanc du cote de la classe contenant la collection.
La difference avec une relation est simplement conceptuelle vu que dans les langages a` objets, limplementation delagregation et la relation est la meme.
-invites
0..* 0..*
ListeInvites Invite
Une liste dinvites nest quune classe pour regrouper des invites. Mais la disparition de la liste nentrane pasnecessairement la disparition des invites. Cest pour cela que dans le cas present une agregation a` ete preferee a` lacomposition.
Classe dassociation
Dans le cas de relation plusieurs a` plusieurs, il est frequent que des valeurs accompagnent la relation. Dans leslangages a` objets, on na dautres choix que de creer une classe specialement pour ces valeurs. A chaque coupledinstances impliquees dans la relation correspond donc une instance de la classe dassociation. La classe dassociationest reliee avec des traits en pointilles a` la relation.
-produits
* *
Commande
- num : int- date : Date
+ getNum() : int+ getDate() : Date
Produit
- num : int- nom : String- prix : int
+ getNum() : int+ getNom() : String+ getPrix() : int
Comporter
-quantite : int
+getQuantite() : int
Le fait quun produit figure sur une commande ne suffit pas a` comple`tement caracteriser leur relation. Il estnecessaire de disposer de la quantite de produit figurant sur cette commande. Comme cette quantite depend a` la foisdu produit et de la commande, celle-ci ne figurer que dans une classe dassociation.
Relations ternaires
Une relation ternaire est un ensemble de triplets mettant en relation trois objets. On lecrit avec un losange relieaux classes de ces trois objets.
19
-
Enseignant
Matiere Classe
Affecter
Une affectation concerne un enseignant, une matie`re et une classe. Ce qui signifie par exemple que chaque enseignantsera en correspondance avec des couples (matie`re/classe).
Relations reflexives
Lorsque chaque instance dune classe contient une reference vers un objet du meme type, on a afaire a` une relationreflexive.
-responsable
0..n
0..1
Salarie
Chaque salarie posse`de un champ responsable referencant lautre salarie qui est son superieur hierarchique.
Relations multiples
Deux classes peuvent etre reliees par plusieurs relations differentes.
-soirees
0..*
-etudiants
0..*
-organisateur
0..*1
Etudiant
- num : int- nom : String- prenom : String
+ getNum() : int+ getNom() : String+ getPrenom() : String
Soiree
- num : int- nom : String- date : Date
+ getNum() : int+ getNom() : String+ getDate() : Date
InscrireInscrire
OrganiserOrganiser
Un etudiant peut aussi bien avoir organise une soiree que sy etre inscrit (voire les deux). Les deux relations nontpas la meme nature et il serait une erreur de les fusionner.
20
-
2.1.5 Exercices
Exercice 1 - Livraisons
Construire un diagramme UML pour le cas Livraisons (vous utiliserez le MCD fait lors des cours precedents).
Exercice 2 - Arbre genealogique
Nous souhaitons mettre au point un logiciel permettant de representer un arbre genealogique. Cest a` dire listagedes personnes, mariages et filiation. Nous tiendrons compte le fait que les parents peuvent etre inconnus. Par contre,nous ne gererons que les mariages heterosexuels et nous ferons abstractions de certains pratiques en vogue comme latransexualite (si vous etes sages nous ferons un TP la`-dessus plus tard dans lannee). Representez cette situation avecun MCD.
Exercice 3 - Bibliothe`que
Nous souhaitons gerer une bibliothe`que simple. Nous recenserons une liste douvrages, avec pour chacun le titre etlauteur (eventuellement plusieurs). On tiendra compte du fait que des ouvrages peuvent exister en plusieurs exem-plaires, certains pouvant ne pas etre disponibles pour le pret (consultables uniquement sur place, ou detruits). Une listedadherents devra etre tenue a` jour, les adhesions devant se renouveler une fois par an. Il devra etre possible de verifierquune adhesion est a` jour (cest-a`-dire quelle a ete renouvelee il y a moins dun an), mais il ne sera pas necessaire deconnatre lhistorique des renouvellements. Les adherents peuvent emprunter jusqua` 5 livres simultanement et chaquelivre emprunte doit etre retourne dans les deux semaines. On devra conserver un historique permettant de savoir quelabonne a emprunte quels livres, les dates demprunts et de retours.
Exercice 4 - Comptes en banque
Nous souhaitons gerer des comptes en banque. Une liste de comptes, avec numero et libelle doit etre tenue a`jour. On souhaitera connatre pour chacun deux lidentite du proprietaire du compte (sachant quun compte peutdans certains cas appartenir a` plusieurs personnes). Pour chaque compte, on conservera lhistorique des modifications(virement, retrait, depot). On considerera comme un virement tout operation impliquant deux comptes et comme desretraits (ou depots) toute operation nimpliquant quun seul compte.
Exercice 5 - Inscriptions sportives
Une ligue sportive souhaite informatiser les inscriptions a` des competitions. Chaque competition porte un nomet une date de cloture des inscriptions. Selon les competitions, les candidats peuvent se presenter seul ou en equipe,sachant que le detail des equipes (liste des candidats et entraneur) devra aussi etre gere.
Exercice 6 - CMS
Nous souhaitons gerer un CMS (content management system). Un CMS est un logiciel permettant de gerer lecontenu dun ou plusieurs sites web. Chaque site porte un nom, est caracterise par une URL, et est decoupe encategories, imbricables les unes dans les autres. Des utilisateurs sont repertories dans le CMS, et chacun peut avoirle droit (ou non) decrire dans un site web. Chaque utilisateur doit avoir la possibilite de publier des articles (ou desbre`ves) dans une categorie dun site web (pourvu quil dispose de droits suffisants dessus). Une bre`ve est composeedun titre et dun contenu textuel. Un article, en plus de son titre et de son texte dintroduction, est constitue dechapitres portant chacun un nom et contenant un texte. Il va de soi quon doit avoir la possibilite pour chaque sitede conserver lhistorique de quel article (ou bre`ve) a ete publie par quel utilisateur. Realisez un diagramme de classesmodelisant cette situation.
21
-
2.2 Design patterns (En construction)
Les design Patterns sont des mode`les permettant de resoudre de facon elegante des proble`mes rencontres frequemmenten programmation objet. Nous en etudierons quelques uns, je vous laisserai le soin de consulter de la documentationsur Internet pour vous familiariser avec les autres.
2.2.1 Factory
Lorsque la creation dun objet doit etre controle, on met loperateur new en private et on en confie lappel a` unemethode generalement static appelee une factory.
tr
rtPrt Prt
Prt
Prt
Exemple
Un client posse`de des commandes, mais une commande nexiste pas sans client. Lorsquune commande est cree sansquun client non null soit specifie, lever une exception peut toujours etre une solution, mais elle presente linconvenientdalourdir le code. Une solution assez elegante consiste a` reduire la visibilite du constructeur de commande et a` creerune methode non statique createCommande dans client. Cette fonction se charge de creer une commande dont le clientest celui a` partir duquel la fonction a ete appelee.
t
t
rt
t
Exercice 1 - Clients et commandes
Creez une classe Commande et une classe Client. Vous reduirez la visibilite du constructeur de Commande et ecrirezune methode createCommande() dans la classe Client. Vous pourrez utiliser une inner class.
2.2.2 Singleton
Le singleton est une classe dont il ne peut exister quune seule instance. Il se code en utilisant une factory.
st
t
t
tt t
Exemple
Lorsquun programme se connecte a` une base de donnees, le fait quil dispose de plusieurs ouvertures simultaneesvers la meme base peut etre une source de bugs tre`s difficiles a` trouver. Le singleton empeche lutilisateur de la classede creer directement une connexion et controle le nombre de connexions.
22
-
Exercice 2 - Singleton
Creez une classe Singleton vide.
2.2.3 Wrapper
Le wrapper est une classe masquant une autre classe. Son but est de dadapter dutilisation dune classe a` unbesoin, ou plus simplement de cacher la classe que vous avez choisi dutiliser.
rr
t
rt
Exemple
Une matrice sutilise avec deux indices, les fonctions permettant de manipuler des collections avec plusieurs indicessont peu commodes et source derreurs.
t
V ector < V ector < T >> tr
tr
tt t
stt t
tr
tt
stt
Exercice 3 - Integer trafique
Ecrire une classe permettant de wrapper un Integer dans une implementation de linterface Anneau presenteedans le diagramme ci-dessous.
23
-
t
tr
tr
tr
tr
r
tr
t
t
tt t
stt t
r
tr tr
tr tr
tr
tt
stt
Exercice 4 - Matrice
Ecrire une classe permettant de gerer une matrice de type T a` deux indices. Vous implementerez les fonctionsde somme et de produit et ferez en sorte que lon puisse faire des matrices de matrices. Le diagramme de classescorrespondant est presente ci-dessus.
2.2.4 Adapter
Ladapteur est limplementation - quelques fois vide - la plus simple que lon peut faire dune interface. Lavantagequelle presente est quelle evite au programmeur decrire un grand nombre de methodes vides ou contenant du coderepetitif pour implementer linterface. Linconvenient est que comme lheritage multiple est interdit dans beaucoup delangages, une classe ne peut heriter que dun adapteur a` la fois.
Attention, dans beaucoup de documentations, ladapteur est assimile a` un wrapper (ce qui si vous y reflechissezbien, est tout a` fait pertinent).
Exemple
Les interfaces comme MouseMotionListener contiennent beaucoup de methodes et il est quelques fois penibledavoir plein de methodes vides dans les classes dimplementation. La classe abstraite MouseMotionAdapter contientune implementation vide de MouseMotionListener et heritant de cette classe il est possible de ne redefinir que lesmethodes dont on a besoin.
2.2.5 Strategy
Lorsque lon souhaite disposer de plusieurs algorithmes dans un projet et choisir lequel utiliser lors de lexecution,ou lors de differentes etapes du projet, les diverses modification a` operer peuvent saverer particulie`rement laides. Lepattern Strategy consiste a` definir une classe me`re representant loperation a` effectuer et dimplementer algorithmedans des classes filles.
24
-
trt
t
tt
t
tt
t
Exemple
Si par exemple, vous souhaitez acceder a` des donnees et que selon la situation le mode dacce`s aux donnees peutchanger (fichier, SGBD, acce`s reseau, etc.). Une facon elegante de proceder est de creer une classe abstraite chargeedacceder aux donnees, et de creer une sous-classe par mode dacce`s.
Exercice 5 - Carre
Creer une classe chargee de calculer le carre dun nombre n. Vous implementerez deux methodes : Calculer directement n2
Utiliser le fait que le carre de n est la somme des n premiers nombres impairs.Vous utiliserez une factory pour permettre a` lutilisateur de choisir la methode de calcul.
2.2.6 Iterator
Les type abstraits de donnees comme les Set, Map ou encore Tree ne dispose pas les elements dans une ordreaussi clair quun tableau ou une liste. iterateur est un moyen dexploiter des collections avec le meme code, en lesparcourant avec une boucle for.
t
tr
tr
trtr trtr
tr
trtr
t
st
r
trt
trtr trtr
ttrtr
t
st
r
Exemple
En java, toute collection heritant de linterface Iterable peut se parcourir avec une boucle de la forme for (Telement : collection)/ .../.
25
-
Exercice 6 - Tableau creux
Creez un wrapper implementant Iterable et encapsulant un tablau. Votre iterateur retournera tous les elementsnon null du tableau. Dans une classe parametree en java, on ne peut pas instancier un tableau T[], vous etes obligede remplacer le tableau par une collection.
t
t
tr
tr
trtr
tr
trtr
t
st
r
r
ts
rt
t
stt
trtr trtr
rtrtr
t
t
st
r
Exercice 7 - Matrice iterable
Rendre iterable la matrice de lexercice sur les wrappers. Ne reinventez pas la roue, utilisez literateur fourni avecle type Vector.
Exercice 8 - Filtre
Creez une interface Condition contenant une methode boolean check(U item). Creez une classe filtre Filtre contenant un Condition et permettant de filtrer une sous-classe T de Iterable. Creez une methodefiltre(Collection condition) retournant un iterable contenant tous les elements de la collection qui verifientcheck.
26
-
t
ts tr
t
ts tr
tr
tr
trtr
tr
trtr
t
st
r
tr
t
t
tr
trt
trtr t tr
trtrtr
t
st
r
2.2.7 Observer
Le mode`le en couche est souvent problematique lorsque deux classes dans des couches differentes ont besoin dinter-agir. LObserver permet deviter les references croisees et de simplifier considerablement le code. Un observer est unobjet surveillant un autre objet, il contient une methode appelee automatiquement lorsquune modification intervientsur lobjet surveille.
srrs
tr
srr
t
tsrr
t
tr
sr
srrsrr
tsrr
Exemple
Dans les interfaces graphiques en Java, il est possible dassocier aux objets graphiques des ActionListener. Linter-face ActionListener contient une seule methode, actionPerformed qui est appelee automatiquement lorsquun utilisateurclique sur un objet graphique. De cette facon, une classe de la bibliothe`que standard de java peut, sans que vous ayeza` la modifier, executer du code que vous avez ecrit.
27
-
tr
tstr
tPrrtt
str
tPrrtt
tr
tt
tstrtstr
Exercice 9 - Surveillance
Reprenez le tableau creux et creez un observateur qui va afficher toutes les modifications survenant dans le tableau.
2.2.8 Proxy
Le proxy cache un objet qui est generalement difficile dacce`s (via une connexion reseau, une lecture sur un fichier,une base de donnees, etc.), et a pour but de masquer la complexite de cet acce`s, ainsi que dappliquer un lazy loading.On parle de lazy loading si un objet est lu que lorsque quelquun le demande.
Lautre avantage du proxy est quil permet via des interfaces de changer la methode de chargement (reseau, basede donnee, etc.).
Exemple
Si lacce`s a` un objet necessite une connexion reseau qui peut prendre du temps, le proxy va le charger une seulefois, et seulement au moment ou` il sera demande.
Exercice 10 - Somme de un a` n
Ecrivez une classe qui calcule la somme des nombres de 1 a` n avec une boucle. Le calcul ne sera fait que la premie`refois que la fonction sera appelee et le resultat sera stocke dans un champ. Les fois suivantes, le resultat ne sera pasrecalcule.
2.2.9 Decorator
Le decorator est un moyen elegant deviter lheritage multiple sans pour autant dupliquer de code. Rappelons quelheritage est en general deconseille (risque de conflit entre les noms de methodes), et dans certains langages (Java)interdit.
Un decorateur est un wrapper qui contient un objet dont le comportement est modifie, la puissance de ce patternvient du fait quun decorateur peut contenir un autre decorateur, il est ainsi possible de placer les decorateurs encascade.
Lavantage du decorateur est quil permet de creer des intersections entre sous-classes et de remplacer lheritagemultiple. Les inconvenients sont de taille : le fait quune liste chanee de decorateurs prece`de un objet est dune partune source de bugs pour les programmeurs inexperimentes, et par ailleurs le compilateur ne peut plus controler le typedes objets de facon aussi precise (nous verrons pourquoi dans les exercices).
Exemple
Si lon souhaite representer des messages affichables en gras, en italique ou en souligne, trois sous-classes ainsi queles multiples combinaisons permettant de recouper ces sous-classes sont necessaires. En utilisant trois wrappers onobtient la possibilite de les combiner.
28
-
ss
ss
ttr tr
ss
ss tr
ttr tr
sstr
rtss
ttr tr
rtssss
tss
ttr tr
tssss
ss
ttr tr
ssss
rss
ttr tr
rssss
Exercice 11 - Messages
Programmez lexemple precedent.
Exercice 12 - Choix de dessert
Implementez la facturation dun desser. Il est possible de choisir des boules de glaces (vanille, fraise et cafe), a` 1euro chacune, sachant quon mettre dans la meme coupe des parfums differents. Lutilisateur peut aussi ajouter de lachantilly (pour 0.5) et le nappage (sauce caramel ou chocolat) est a` 0.75 euros.
29
-
Annexe A
Quelques Corriges
A.1 Dependances fonctionnelles
Secretariat pedagogique
dateinsc
numetud
numform
nummod
numsemestre
adr1etud
adr2etud
cpetud villeetud
nomsemestre
nommod
nomform
nometud
prenometud
A.2 MCD
Livraisons
0,N 0,N
PROP
0,N
R
0,N
TER
UIT
numprou
30
-
A.3 UML
Arbre genealogique
r
r
Prs
t
tr
r tr
t t
t tr
tPr tr
Bibliothe`que
-ouvrages
*
-auteurs
*-ouvrage*
-emprunts
-exemplaires
*
-emprunts
-adherents*
Personne
- num : int- nom : String- prenom : String
+ getNum() : int+ getNom() : String+ getPrenom() : String
Auteur
Ouvrage
- codeISBN : String- titre : String
+ getCodeISBN() : String+ getTitre() : String
Exemplaire
- num : int
+ getNum() : int
Disponible
Adherent
- dateRenouvellement : Date
+ getDateRenouvellement() : Date
Emprunter
- dateEmprunt : Date- dateRetour : Date
31
-
Banque
-clients
1..*
-comptes
1..*
-operations 1..2
*
-compte
*
-emetteur
*
-destinataire
*
Client
- num : int- nom : String- prenom : String
Compte
- num : int- nom : String
+ getNum() : int+ getNom() : String
Operation
- montant : double- libelle : String- date : Date
Virement
OperationLocale
Depot Retrait
32
-
InsriptionsSportives
-membres
1..*
-equipes
*
-entraineur1
-equipesEntrainees*
-competitions
*
-candidats
*
Competition
- num : int- nom : String- dateCloture : Date
Personne
- num : int- nom : String- prenom : String
+ getNum() : int+ getNom() : String+ getPrenom() : String
Equipe
Candidat
CMS
trPrt
trss
sts
tr
ts
trs
rt
ts
tr
trs
st
t
str
r tr
tstr
t
tr
r tr
tr
tr
Pt
ttr tr
t t
r
t tr
rt
trt tr
tr
tr
tt tr
33
-
A.4 Design patterns
A.4.1 Factory
Clients et commandes
package factory ;
class Client
{public Commande createCommande ( ){
return new Commande ( ) ;}
class Commande
{private Commande ( ){}
}}
public class Factory
{public stat ic void main ( String [ ] args ){
Client c = new Client ( ) ;@SuppressWarnings ("unused" )Client . Commande cm = c . createCommande ( ) ;
}}
A.4.2 Singleton
package singleton ;
public class Singleton
{private stat ic Singleton singleton ;
private Singleton ( ){}
public stat ic Singleton getSingleton ( ){
i f ( singleton == null )singleton = new Singleton ( ) ;
return singleton ;}
public stat ic void main ( String [ ] args ){
Singleton s1 = getSingleton ( ) , s2 = getSingleton ( ) ;System . out . println ( s1 == s2 ) ;
}
}
34
-
A.4.3 Wrapper
Integer trafique
package wrapper ;
interface Anneau
{public T zero ( ) ;public T un ( ) ;public T add (T other ) ;public T mul (T other ) ;
}
public class IntegerTraffique implements Anneau
{private Integer integer ;
public IntegerTraffique ( Integer integer ){
this . integer = integer ;}
public Integer get ( ){
return integer ;}
@Override
public IntegerTraffique zero ( ){
return new IntegerTraffique (0 ) ;}
@Override
public IntegerTraffique un ( ){
return new IntegerTraffique (1 ) ;}
@Override
public IntegerTraffique add ( IntegerTraffique other ){
return new IntegerTraffique ( get ( ) + other . get ( ) ) ;}
@Override
public IntegerTraffique mul ( IntegerTraffique other ){
return new IntegerTraffique ( get ( ) other . get ( ) ) ;}
@Override
public String toString ( ){
return integer . toString ( ) ;}
}
35
-
Matrice
package wrapper ;
import java . util . Iterator ;import java . util . Vector ;
class Matrice implements Anneau, Iterable{
private Vector matrice ;private int nbL , nbC ;
public Matrice ( int nbL , int nbC , T init ){
this . nbL = nbL ;this . nbC = nbC ;matrice = new Vector(nbL ) ;for ( int i = 0 ; i < nbL ; i++){
matrice . add (new Vector(nbC ) ) ;for ( int j = 0 ; j < nbC ; j++)
matrice . get (i ) . add ( init ) ;}
}
public Matrice ( int nbL , int nbC ){
this ( nbL , nbC , null ) ;}
public T get ( int i , int j ){
return matrice . get (i ) . get (j ) ;}
public void set ( int i , int j , T item ){
i f ( item != null )matrice . get (i ) . set (j , item ) ;
else
set (i , j , get (0 , 0) . zero ( ) ) ;}
@Override
public Matrice add ( Matrice other ){
i f ( nbC != other . nbC && nbL != other . nbL )throw new java . lang . IllegalArgumentException ( ) ;
Matrice result = new Matrice(nbL , other . nbC , null ) ;for ( int i = 0 ; i < nbL ; i++)
for ( int j = 0 ; j < nbC ; j++)result . set (i , j , get (i , j ) . add ( other . get (i , j ) ) ) ;
return result ;}
@Override
public Matrice mul ( Matrice other ){
i f ( nbC != other . nbL )
36
-
throw new java . lang . IllegalArgumentException ( ) ;T zero = get (0 , 0) . zero ( ) ;Matrice result = new Matrice(nbL , other . nbC , zero ) ;for ( int i = 0 ; i < nbL ; i++)
for ( int j = 0 ; j < other . nbC ; j++)for ( int k = 0 ; k < nbC ; k++)
result . set (i , j , result . get (i , j ) .add ( get (i , k ) . mul ( other . get (k , j ) ) ) )
;return result ;
}
@Override
public Matrice zero ( ){
return new Matrice(nbL , nbC , get (0 , 0) . zero ( ) ) ;}
@Override
public Matrice un ( ){
Matrice un = new Matrice(nbL , nbL , get (0 , 0) . zero ( ) ) ;for ( int i = 0 ; i < nbL ; i++)
un . set (i , i , get (0 , 0) . un ( ) ) ;return un ;
}
@Override
public String toString ( ){
String res = "" ;for ( Vector vector : matrice ){
res += "[ " ;for (T item : vector )
res += item + " " ;res += "]\n" ;
}return res ;
}
@Override
public Iterator iterator ( ){
return new IterateurMatrice(matrice . iterator ( ) ) ;}
}
public class Wrapper
{public stat ic void main ( String [ ] args ){
Matrice
m = new Matrice(2 , 2 , new IntegerTraffique (2 ) ) ,un = m . un ( ) , zero = m . zero ( ) ;
System . out . println (m ) ;System . out . println ( un ) ;System . out . println ( zero ) ;System . out . println (m . add ( un ) ) ;
37
-
System . out . println (m . mul (m ) ) ;}
}
A.4.4 Strategy
Carre
package strategy ;
public abstract class Square
{public enum Algo {DIRECT , SUM } ;
public abstract long square ( long n ) ;
public stat ic Square getSquare ( Algo algo ){
switch ( algo ){
case DIRECT : return new DirectSquare ( ) ;case SUM : return new SumSquare ( ) ;
}return null ;
}
public stat ic void main ( String [ ] args ){
Square direct = getSquare ( Algo . DIRECT ) , sum = getSquare ( Algo . SUM ) ;for ( int i = 1 ; i
-
A.4.5 Iterateur
Tableau creux
package iterator ;
import java . util . Iterator ;import java . util . Vector ;
public class TableauCreux implements Iterable
{private Vector tableauCreux ;
public TableauCreux ( int size ){
tableauCreux = new Vector(size ) ;for ( int i = 0 ; i < size ; i++)
tableauCreux . add ( null ) ;}
public T get ( int i ){
return tableauCreux . get (i ) ;}
public void set ( int i , T item ){
tableauCreux . set (i , item ) ;}
@Override
public java . util . Iterator iterator ( ){
return new TableauCreuxIterator ( tableauCreux . iterator ( ) ) ;}
private class TableauCreuxIterator implements Iterator
{private java . util . Iterator iterator ;private T item = null ;
TableauCreuxIterator ( Iterator iterator ){
this . iterator = iterator ;}
@Override
public boolean hasNext ( ){
while ( item == null && iterator . hasNext ( ) )item = iterator . next ( ) ;
return item != null ;}
@Override
public T next ( ){
T result = item ;item = null ;return result ;
39
-
}@Override
public void remove ( ){
iterator . remove ( ) ;}
}
@Override
public String toString ( ){
String res = "[ " ;for (T item : this )
res += item + " " ;return res + "]" ;
}
public stat ic void main ( String [ ] args ){
TableauCreux tc = new TableauCreux(10) ;tc . set (6 , 5) ;tc . set (2 , 90) ;System . out . println ( tc ) ;
}}
Matrice Iterable
package wrapper ;
import java . util . Iterator ;import java . util . Vector ;
public class IterateurMatrice implements Iterator
{private Iterator lines = null ;private Iterator line = null ;
public IterateurMatrice ( Iterator iterator ){
lines = iterator ;}
@Override
public boolean hasNext ( ){
while ( line == null | | ! line . hasNext ( ) && lines . hasNext ( ) )line = lines . next ( ) . iterator ( ) ;
return line . hasNext ( ) ;}
@Override
public T next ( ){
return line . next ( ) ;}
40
-
@Override
public void remove ( ){
line . remove ( ) ;}
public stat ic void main ( String [ ] args ){
Matrice m =new Matrice(2 , 2 , new IntegerTraffique (2 ) )
;for ( IntegerTraffique i : m . add (m . un ( ) ) )
System . out . print (i + " " ) ;}
}
Filtre
package iterator ;
import java . util . ArrayList ;import java . util . Iterator ;
interface Condition
{public boolean check (U item ) ;
}
public class Filtre{
private f ina l Condition condition ;
public Filtre ( Condition filterFunction ){
this . condition = filterFunction ;}
public Iterable iterator ( f ina l T collection ){
return new Iterable(){
@Override
public Iterator iterator ( ){
return new Iterator(){
private Iterator iterator = collection . iterator ( );
private U next = null ;
@Override
public boolean hasNext ( ){
boolean res = fa l se ;while ( iterator . hasNext ( ) && ! res ){
next = iterator . next ( ) ;res = condition . check ( next ) ;
41
-
}return res ;
}
@Override
public U next ( ){
return next ;}
@Override
public void remove ( ){
iterator . remove ( ) ;}
} ;}
} ;}
public stat ic void main ( String [ ] args ){
ArrayList array = new ArrayList() ;for ( int i = 22 ; i
-
{private Set observers = new HashSet() ;
public TableauxCreuxObserver ( int size ){
super ( size ) ;}
public void notifyObserver ( int index ){
for ( IndexObserver observer : observers )observer . notify ( index ) ;
}
@Override
public void set ( int i , T item ){
super . set (i , item ) ;notifyObserver (i ) ;
} ;
@Override
public void notify ( int index ){
System . out . println ("Value (index = " + index + " has changed to " + get (index ) ) ;
}
@Override
public void add ( IndexObserver observer ){
this . observers . add ( observer ) ;}
@Override
public void remove ( IndexObserver observer ){
this . observers . remove ( observer ) ;}
}
public class SurveillanceTableauCreux
{public stat ic void main ( String [ ] args ){
f ina l int SIZE = 10 ;TableauxCreuxObserver tco = new TableauxCreuxObserver(SIZE
) ;tco . add ( tco ) ;Random r = new Random ( ) ;for ( int i = 1 ; i < SIZE ; i++)
tco . set ( Math . abs (r . nextInt ( ) )%SIZE , r . nextInt ( ) ) ;}
}
A.4.7 Proxy
Somme
43
-
package proxy ;
class Somme
{private long n , sum = 0 ;private boolean done = fa l se ;
public Somme ( long n ){
this . n = n ;}
public long getSomme ( ){
i f ( ! done )for ( long i = 1 ; i
-
this . message = message ;}
@Override
public String toString ( ){
return message ;}
}
abstract class MessageDecorator extends Message
{private Message message ;
public MessageDecorator ( Message message ){
this . message = message ;}
@Override
public String toString ( ){
return message . toString ( ) ;}
}
class BoldMessage extends MessageDecorator
{public BoldMessage ( Message message ){
super ( message ) ;}
@Override
public String toString ( ){
return "" + super . toString ( ) + "" ;}
}
class ItalicMessage extends MessageDecorator
{public ItalicMessage ( Message message ){
super ( message ) ;}
@Override
public String toString ( ){
return "" + super . toString ( ) + "" ;}
}
class UnderlinedMessage extends MessageDecorator
{public UnderlinedMessage ( Message message ){
super ( message ) ;
45
-
}@Override
public String toString ( ){
return "" + super . toString ( ) + "" ;}
}
Dessert
package decorator ;
abstract class AbstractGlace
{private AbstractGlace glace = null ;
public AbstractGlace ( AbstractGlace glace ){
this . glace = glace ;}
public abstract double getPrix ( ) ;public abstract String getLib ( ) ;
public double getAddition ( ){
return getPrix ( ) + ( ( glace != null ) ? glace . getAddition ( ) : 0) ;}
@Override
public String toString ( ){
return ( ( glace != null ) ? glace + "\n" : "" ) +"* " + getLib ( ) + " : " + getPrix ( ) ;
}}
class BouleGlace extends AbstractGlace
{public enum Parfum {CHOCOLAT , VANILLE , FRAISE } ;private int nbBoules ;private Parfum parfum ;
public BouleGlace ( AbstractGlace glace , int nbBoules , Parfum parfum ){
super ( glace ) ;this . nbBoules = nbBoules ;this . parfum = parfum ;
}
@Override
public double getPrix ( ){
return nbBoules ;}
@Override
46
-
public String getLib ( ){
return nbBoules + " boule(s) parfum " + parfum ;}
}
class Chantilly extends AbstractGlace
{
public Chantilly ( AbstractGlace glace ){
super ( glace ) ;}
@Override
public double getPrix ( ){
return 0 . 5 ;}
@Override
public String getLib ( ){
return "Chantilly" ;}
}
class Nappage extends AbstractGlace
{private Parfum parfum ;public enum Parfum {CHOCOLAT , CARAMEL } ;
public Nappage ( AbstractGlace glace , Parfum parfum ){
super ( glace ) ;this . parfum = parfum ;
}
@Override
public double getPrix ( ){
return 0 . 7 5 ;}
@Override
public String getLib ( ){
return "Nappage " + parfum ;}
}
public class Glace
{public stat ic void main ( String [ ] args ){
AbstractGlace glace = new Nappage (new Chantilly (new BouleGlace (new BouleGlace (null , 1 , BouleGlace . Parfum .
CHOCOLAT ) , 2 , BouleGlace . Parfum . VANILLE ) ), Nappage . Parfum . CARAMEL ) ;
47
-
System . out . println ( glace ) ;System . out . println ("total : " + glace . getAddition ( ) ) ;
}}
48