7 de la conception à l'implementationefreidoc.fr/L2 -...
Transcript of 7 de la conception à l'implementationefreidoc.fr/L2 -...
-
1
De la conception à l’implémentation
Implémentation des agrégations
-
2
Implémentation des agrégations en C++ (1/5)
Benoît Charroux - De la conception à l’implémentation- Juillet 99 - 3
class Moteur{private :
char* type ;public :
Moteur( const char* ) ;~Moteur() ;Moteur( const Moteur & ) ;Moteur & operator = ( const Moteur & ) ;
} ;
#include "moteur.h"class Voiture{private :
char* marque ;��������������
����������
public :Voiture( const char* marqueVoiture, const char* marqueMoteur ) ;~Voiture() ;Voiture( const Voiture & ) ;Voiture & operator = ( const Voiture & ) ;
} ;
• Agrégation en déclarant un objet dans un autre :
Implémentation de la classe moteur (2/5)
Benoît Charroux - De la conception à l’implémentation- Juillet 99 - 4
Moteur::Moteur( const char* nom ){type = new char[ strlen(nom) + 1 ] ;strcpy( type, nom ) ;
}Moteur::~Moteur(){
delete [] type ;}Moteur::Moteur( const Moteur & v ){ // constructeur par recopie ...
type = new char[ strlen(v.type) + 1 ] ; // s’il y a des parties dynamiquesstrcpy( type, v.type ) ;
}Moteur & Moteur::operator = ( const Moteur & v ){ // opérateur d’affectation
if( this != &v ){ // s’il y a des partiesdelete [] type ; // dynamiquestype = new char[ strlen(v.type) + 1 ] ;strcpy( type, v.type ) ;
}return *this ;
}
-
3
Implémentation de la classe voiture (3/5)
Benoît Charroux - De la conception à l’implémentation- Juillet 99 - 5
• La copie de l’agrégat entraîne la copie de l’agrégé :
voiture1 : Voiture
voiture2 : Voiture
moteur1 : Moteur
moteur1 : Moteur
copie copie
Voiture::Voiture( const Voiture & v ) �������������������� {// appel du constructeur ...marque = new char[ strlen(v.marque) + 1 ] ; // par recopie de la classe ...strcpy( marque, v.marque ) ; // moteur
}
• Appel du constructeur par recopie de la classe Moteur dans le constructeur par recopie de la classe Voiture :
Implémentation de la classe voiture (4/5)
Benoît Charroux - De la conception à l’implémentation- Juillet 99 - 6
voiture1 : Voiture
voiture2 : Voiture
moteur1 : Moteur
moteur1 : Moteur
• La destruction de l’agrégat entraîne la destruction de l’agrégé :
Voiture::~Voiture(){delete [] marque ;
}
• Appel automatique du destructeur de Moteur :
-
4
Implémentation de la classe voiture (fin) (5/5)
Benoît Charroux - De la conception à l’implémentation- Juillet 99 - 7
// constructeurVoiture::Voiture( const char* marqueVoiture, const char* marqueMoteur ) :
������� ������������ � { // appel du constructeur de la classe Moteurmarque = new char[ strlen(marqueVoiture) + 1 ] ;strcpy( marque, marqueVoiture ) ;
}
// surcharge de l’opérateur =Voiture & Voiture::operator = ( const Voiture & v ){
if( this != &v ){������������������ // appel de l’opérateur = de la classe Moteurdelete [] marque ;marque = new char[ strlen(v.marque) + 1 ] ;strcpy( marque, v.marque ) ;
}return *this ;
}
Implémentation d’une agrégation par un pointeur (1/3)
Benoît Charroux - De la conception à l’implémentation- Juillet 99 - 8
#include "moteur.h »class Voiture{private :
���������������
�����������������������char* marque ;
public :Voiture( const char* marqueVoiture, const char* marqueMoteur ) ;
�������������������
���������
~Voiture() ;Voiture( const Voiture & ) ;Voiture & operator = ( const Voiture & ) ;
} ;
• L’implémentation d’une agrégation par un pointeur à l’avantage :
• de bénéficier du polymorphisme ;
• de permettre l’adoption (l’agrégation ne se fait pas à la construction des objets mais n’importe quand).
-
5
Implémentation de la classe Voiture (2/3)
Benoît Charroux - De la conception à l’implémentation- Juillet 99 - 9
// constructeurVoiture::Voiture( const char* marqueVoiture, const char* marqueMoteur ) : �������������������������������� {
marque = new char[ strlen(marqueVoiture) + 1 ] ;strcpy( marque, marqueVoiture ) ;
}
// destructeurVoiture::~Voiture(){
������ �������delete [] marque ;
}
// adoption���������������������������������������������
Implémentation de la classe voiture (fin) (3/3)
Benoît Charroux - De la conception à l’implémentation- Juillet 99 - 10
// constructeur par recopieVoiture::Voiture( const Voiture & v ) : �������������������������������� {
marque = new char[ strlen(v.marque) + 1 ] ;strcpy( marque, v.marque ) ;
}
// opérateur d’affectationVoiture & Voiture::operator = ( const Voiture & v ){
if( this != &v ){����������������������delete [] marque ;marque = new char[ strlen(v.marque) + 1 ] ;strcpy( marque, v.marque ) ;
}return *this ;
}
-
6
Implémentation des associations
en C++
Modéliser les associations par des attributs
• Selon la cardinalités des associations des attributs peuvent être placés :
• dans une des classes pour les associations de 1 vers 1 ;
• dans la classe côté N pour les associations de 1 vers N ;
• il est possible de promouvoir une association au rang de classe pour augmenter la lisibilité.
Benoît Charroux - De la conception à l’implémentation- Juillet 99 - 12
-
7
Modéliser les associations par des attributs
• Pour placer des attributs, il faut déterminer si une association se traduit par un lien unidirectionnel ou bidirectionnel :
• unidirectionnel : un seul attribut est alors nécessaire ;
• bidirectionnel : deux attributs ou une classe d’association sont nécessaires.
Exemple tiré de la gestion d’une médiathèque
Lien unidirectionnel
Liens bidirectionnels
Benoît Charroux - De la conception à l’implémentation- Juillet 99 - 13
Implémentation d’une association unidirectionnelle en C++ (1/2)
Benoît Charroux - De la conception à l’implémentation- Juillet 99 - 14
class Emplacement ;class Exemplaire{
����� ������������ ������public :
Exemplaire() ;// mise a jour de l’associationvoid setEmplacement( Emplacement* emplacement ) ;Emplacement* getEmplacement() ;
} ;
class Emplacement{int rayon ;
public :// ...
} ;
void main(){Emplacement emplacement ;Exemplaire exemplaire ;exemplaire.setEmplacement( &emplacement ) ;Emplacement* place = exemplaire.getEmplacement() ;
}
• Une association unidirectionnelle s’implémente à l’aide d’un pointeur.
-
8
Implémentation d’une association unidirectionnelle en C++ (2/2)
Benoît Charroux - De la conception à l’implémentation- Juillet 99 - 15
Exemplaire::Exemplaire(){emplacement = NULL ;
}void Exemplaire::setEmplacement( Emplacement* emplacement ){
this->emplacement = emplacement ;}Emplacement* Exemplaire::getEmplacement(){
return emplacement ;}
• Implémentation de la classe Exemplaire :
Association unidirectionnelle de 1 vers plusieurs en C++ (1/3)
Benoît Charroux - De la conception à l’implémentation- Juillet 99 - 16
void main(){Entreprise monEntreprise( "Mon entreprise" ) ;
Client client1( 1 ) ; // création d’un clientmonEntreprise.addClient( client1 ) ; // ajoute un client à l’entreprise
Client client2( 2 ) ; // création d’un deuxième clientmonEntreprise.addClient( client2 ) ; // ajoute un deuxième client
monEntreprise.removeClient( client1 ) ; // supprime le premier client}
• Une association unidirectionnelle s’implémente à l’aide d’un tableau de pointeurs, d’un vecteur, ...
-
9
Association unidirectionnelle de 1 vers plusieurs en C++ (2/3)
Benoît Charroux - De la conception à l’implémentation- Juillet 99 - 17
// vecteurs de clients�!����"��� ���#$�����%�$&'�()*�
class Entreprise{string nom ;// association entreprise / clients$&'�()*� �����+�
public :Entreprise( const string & ) ;string getNom() ;// mise a jour de l’associationvoid addClient( Client & ) ;void removeClient( const Client & ) ;const CLIENTS & getClients() ;
} ;
class Client{int numero ;
public :Client( int numero ) ;int getNumero() ;int operator == ( const Client & ) ;int operator != ( const Client & ) ;
} ;
• Utilisation des vecteurs de la Standard Template Library.
Association unidirectionnelle de 1 vers plusieurs en C++ (3/3)
Benoît Charroux - De la conception à l’implémentation- Juillet 99 - 18
void Entreprise::addClient( Client & client ){int i = 0 ; // cherche si le client est déjà présentwhile( i
-
10
Association bidirectionnelle de 1 vers 1 en C++ (1/3)
Benoît Charroux - De la conception à l’implémentation- Juillet 99 - 19
void main(){Homme h ;Femme f ;h.setFemme( &f ) ;
}
class Homme ;class Femme{
public :Homme* homme ;Homme* GetHomme() ;void setHomme( Homme* ) ;
} ;
class Femme ;class Homme{
public :Femme* femme ;Femme* GetFemme() ;void setFemme( Femme* ) ;
} ;
• Les attributs de l’association sont publics => on peut les manipuler directement et individuellement, or la mise à jour doit être faite simultanément des deux cotés de l’association.
• Une association bidirectionnelle s’implémente à l’aide d’un pointeurs dans chaque classe :
Association bidirectionnelle de 1 vers 1 en C++ (2/3)
Benoît Charroux - De la conception à l’implémentation- Juillet 99 - 20
Homme* Femme::GetHomme(){
return homme ;}void Femme::setHomme( Homme* homme ){
this->homme = homme ;homme->femme = this ;
}
Femme* Homme::GetFemme(){
return femme ;}void Homme::setFemme( Femme* femme ){
this->femme = femme ;femme->homme = this ;
}
-
11
Solution partielle pour éviter les attributs publics:fonctions amies(3/3)
Benoît Charroux - De la conception à l’implémentation- Juillet 99 - 21
#include "femme.h"class Homme{
private :Femme* femme ;"���������� ,������+��-������-��������
public :Femme* GetFemme() ;void setFemme( Femme* ) ;
} ;class Homme ;class Femme{
public :Homme* homme ;Homme* GetHomme() ;void setHomme( Homme* ) ;
} ;
Fonction ayant accès à l’attribut femme.
Attribut privé
Association bidirectionnelle de 1 vers plusieurs en C++ (1/6)
Benoît Charroux - De la conception à l’implémentation- Juillet 99 - 22
typedef vector EXEMPLAIRES ;class Oeuvre{
// ...�.��/&0'1�*��2��������+��
public :// ...
} ;
void main(){Oeuvre donGiovani( "Don Govani" ) ;Exemplaire exp1( 10 ) ;donGiovani.addExemplaire( exp1 ) ;
}
• Parcours de l’association dans le sens Œuvre -> Exemplaire :
class Exemplaire{// ...
public :3������ ������ // ...
} ;
-
12
Association bidirectionnelle de 1 vers plusieurs en C++ (2/6)
Benoît Charroux - De la conception à l’implémentation- Juillet 99 - 23
• Déclaration de la classe Oeuvre :
typedef vector EXEMPLAIRES ;class Oeuvre{
string titre ;EXEMPLAIRES exemplaires ; // association œuvre / exemplaires
public :Oeuvre( const string & titre ) ;string getTitre() ;// fonctions ayant acces a l'association exemplairesfriend void Exemplaire::addOeuvre( Oeuvre & ) ;friend void Exemplaire::removeOeuvre( Oeuvre & ) ; // mise a jour de l'associationvoid addExemplaire( Exemplaire & ) ;void removeExemplaire( const Exemplaire & ) ;const EXEMPLAIRES & getExemplaires() ;void affiche() ;
} ;
Association bidirectionnelle de 1 vers plusieurs en C++ (3/6)
Benoît Charroux - De la conception à l’implémentation- Juillet 99 - 24
void Oeuvre::addExemplaire( Exemplaire & exemplaire ){int i = 0 ; // cherche si l’exemplaire est deja presentwhile( i
-
13
Association bidirectionnelle de 1 vers plusieurs en C++ (4/6)
Benoît Charroux - De la conception à l’implémentation- Juillet 99 - 25
void main(){Oeuvre donGiovani( "Don Govani" ) ;Exemplaire exp1( 10 ) ;exp1.addOeuvre( donGiovani ) ;
}
• Parcours de l’association dans le sens Exemplaire -> Œuvre :
Association bidirectionnelle de 1 vers plusieurs en C++ (5/6)
Benoît Charroux - De la conception à l’implémentation- Juillet 99 - 26
class Oeuvre ;class Exemplaire{
int numero ;public :
3������ ������ �
��++� �������7�������2��������+Exemplaire( int numero ) ;// mise a jour de l’associationvoid addOeuvre( Oeuvre & ) ;void removeOeuvre( Oeuvre & ) ;
int operator == ( const Exemplaire & ) ;int operator != ( const Exemplaire & ) ;
} ;
• Déclaration de la classe Exemplaire :
-
14
Association bidirectionnelle de 1 vers plusieurs en C++ (6/6)
Benoît Charroux - De la conception à l’implémentation- Juillet 99 - 27
void Exemplaire::addOeuvre( Oeuvre & oeuvre ){int i = 0 ; // cherche si l’exemplaire est deja presentwhile( ioeuvre = &oeuvre ; // mise a jour du lien avec l’exemplaire
}else throw "cette exemplaire est deja reference" ;}void Exemplaire::removeOeuvre( Oeuvre & oeuvre ){
int i = 0 ;EXEMPLAIRES::iterator theIterator ; // parcours des exemplairestheIterator = oeuvre.exemplaires.begin(); // se positionne sur le premierwhile( ioeuvre = NULL ;
}else throw "exemplaire inconnu" ;}
Association bidirectionnelle de 1 vers plusieurs en C++ (1/6)
Benoît Charroux - De la conception à l’implémentation- Juillet 99 - 28
• Modélisation d’une association bidirectionnelle par une classe d’association ;
• utilisation d’une table de hachage de la STL (map) : un ensemble d’œuvres (vecteur) est accessible par un nom d’auteur (clef).
typedef vector OEUVRES ;typedef map DICO_AUTEUR_OEUVRES ;class Oeuvre{
// ...8'$390:)�:193�:�1�*��� ��
public :// ...
} ;
class Oeuvre ;class Auteur{
// ...public :
// ...// fonction pour comparer deux clefs de type auteur (voir oeuvre.h)bool operator()( const Auteur & s1, const Auteur & s2 ) const ;
} ;
-
15
Association bidirectionnelle de 1 vers plusieurs en C++ (2/6)
Benoît Charroux - De la conception à l’implémentation- Juillet 99 - 29
• Déclaration de la classe Œuvre :
typedef vector OEUVRES ;typedef map DICO_AUTEUR_OEUVRES ;class Oeuvre{
string titre ;DICO_AUTEUR_OEUVRES dico ;friend void Auteur::addOeuvre( Oeuvre & oeuvre ) ;friend void Auteur::removeOeuvre( Oeuvre & oeuvre ) ;
public :Oeuvre( const string & titre ) ;string getTitre() ;// mise a jour de l’association auteur/oeuvresvoid addAuteur( Auteur & ) ; // ajout d’un auteur au dicovoid removeAuteur( Auteur & ) ; // suppression d’un auteur du dicoDICO_AUTEUR_OEUVRES & getDico() ;// pour comparer deux oeuvres (voir Auteur::addOeuvre() )bool operator == ( const Oeuvre & ) ;bool operator != ( const Oeuvre & ) ;
} ;
Association bidirectionnelle de 1 vers plusieurs en C++ (3/6)
Benoît Charroux - De la conception à l’implémentation- Juillet 99 - 30
• Implémentation de la classe Œuvre :
void Oeuvre::addAuteur( Auteur & auteur ){DICO_AUTEUR_OEUVRES::iterator iter ;iter = dico.find( auteur ) ; // cherche si auteur est une clefif( iter == dico.end() ){ // si l’auteur n’est pas une clef
OEUVRES oeuvres ; // cree un vecteur d’oeuvresoeuvres.push_back( *this ) ; // ajoute l’oeuvre courantepairp ;p = dico.insert(DICO_AUTEUR_OEUVRES::value_type(auteur,oeuvres));
}else{ // si auteur est deja une clef OEUVRES::iterator theIterator ; int i = 0 ;theIterator = (*iter).second.begin(); // l’oeuvre courante est-elle liee a cet auteurwhile( i
-
16
Association bidirectionnelle de 1 vers plusieurs en C++ (4/6)
Benoît Charroux - De la conception à l’implémentation- Juillet 99 - 31
• Implémentation de la classe Œuvre :
void Oeuvre::removeAuteur( Auteur & auteur ){if ( dico.erase( auteur ) != 1) throw "effacement impossible" ;
}
• Déclaration de la classe Auteur :
class Oeuvre ;class Auteur{
string nom ;public :
Auteur( const string & = "" ) ;// mise a jour de l’association auteur/oeuvresvoid addOeuvre( Oeuvre & ) ; // ajoute une oeuvre a l’auteurvoid removeOeuvre( Oeuvre & ) ; // supprime une oeuvre a l’auteur// fonction pour comparer deux clefs de type auteur (voir oeuvre.h)bool operator()( const Auteur & s1, const Auteur & s2 ) const ;
} ;
Association bidirectionnelle de 1 vers plusieurs en C++ (5/6)
Benoît Charroux - De la conception à l’implémentation- Juillet 99 - 32
• Implémentation de la classe Auteur :
void Auteur::addOeuvre( Oeuvre & oeuvre ){DICO_AUTEUR_OEUVRES::iterator iter ;iter = oeuvre.dico.find( *this ) ; // cherche si l’auteur courant est une clefif( iter == oeuvre.dico.end() ){ // si l’auteur n’est pas une clef
OEUVRES oeuvres ; // cree un vecteur d’oeuvresoeuvres.push_back( oeuvre ) ; // y ajoute l’oeuvrepairp ;p = oeuvre.dico.insert(DICO_AUTEUR_OEUVRES::value_type(*this,oeuvres));if( p.second == false ) throw "insertion impossible" ;
}else{ // si l’auteur est une clefOEUVRES::iterator theIterator ; int i = 0 ; // cherche si l’oeuvre est deja presentetheIterator = (*iter).second.begin();while( i
-
17
Association bidirectionnelle de 1 vers plusieurs en C++ (6/6)
Benoît Charroux - De la conception à l’implémentation- Juillet 99 - 33
• Implémentation de la classe Auteur :
void Auteur::removeOeuvre( Oeuvre & oeuvre ) {DICO_AUTEUR_OEUVRES::iterator iter ;iter = oeuvre.dico.find( *this ) ; // cherche si l’auteur courant est une clefif( iter == oeuvre.dico.end() ) // si l’auteur n’est pas une clef
throw "L’auteur courant n’est pas dans le dictionnaire" ;else{ // si l’auteur est une clef
OEUVRES::iterator theIterator ;int i = 0 ;theIterator = (*iter).second.begin(); // se positionne sur la premiere oeuvrewhile( i
-
18
Implémentation d’une association unidirectionnelle en java
Benoît Charroux - De la conception à l’implémentation- Juillet 99 - 35
• Une association unidirectionnelle s’implémente à l’aide d’une référence :
class Exemplaire{������� ����� ����������� ������
public void setEmplacement( Emplacement emplacement ){this.emplacement = emplacement ;
}public Emplacement getEmplacement(){
return emplacement ;}public static void main( String [] argv ){
Emplacement emplacement = new Emplacement() ;Exemplaire exemplaire = new Exemplaire() ; // création d’un exemplaireexemplaire.setEmplacement( emplacement ) ; // ajout de l’exemplaireEmplacement place = exemplaire.getEmplacement() ; // récupération de l’emplacement
}}
class Emplacement{private int rayon ;// ...
}
Association unidirectionnelle de 1 vers plusieurs en java (1/3)
Benoît Charroux - De la conception à l’implémentation- Juillet 99 - 36
public static void main( String [] argv ){Entreprise monEntreprise = new Entreprise( "Mon entreprise" ) ;Client client1 = new Client( 10 ) ; // création d’un clienttry{
monEntreprise.addClient( client1 ) ; // ajout du clientClient client2 = new Client( 20 ) ; // création d’un clientmonEntreprise.addClient( client2 ) ; // ajout du clienttry{
monEntreprise.removeClient( client2 ) ; // suppression d’un client} catch( ClientNonReferenceException e ) {
System.out.println( e ) ;}
} catch ( ClientDejaReferenceException e ) {System.out.println( e ) ;
}
• Une association unidirectionnelle s’implémente à l’aide d’un vecteur, ...
-
19
Association unidirectionnelle de 1 vers plusieurs en java (2/3)
Benoît Charroux - De la conception à l’implémentation- Juillet 99 - 37
• Implémentation de la classe Entreprise :
import java.util.Vector ;class Entreprise{
private String nom ;���������� ��� �����+������ �� ������
��++� ���������������+��� �����+public Entreprise( String nom ){
this.nom = nom ;}public void addClient( Client client ) throws ClientDejaReferenceException{
if( clients.contains( client ) == false ) // si le client est déjà référencé ...clients.addElement( client ) ; // on l’ajoute
elsethrow new ClientDejaReferenceException( "Client deja present" ) ;
}public void removeClient( Client client ) throws ClientNonReferenceException{
if( clients.removeElement( client ) == false ) // si le client est inconnuthrow new ClientNonReferenceException( "Client inconnu de l'entreprise" ) ;
}}
Association unidirectionnelle de 1 vers plusieurs en java (3/3)
Benoît Charroux - De la conception à l’implémentation- Juillet 99 - 38
• Implémentation de la classe Client :
class Client{private int numero ;public Client( int numero ){
this.numero = numero ;}public int getNumero(){
return numero ;}
// fonction utilisée par contains de Vector pour savoir si un client // est déjà présent : 2 clients sont égaux s’ils ont même numéro
public boolean equals( Object obj ){if( (obj!=null) && (obj instanceof Client) )
return numero == ((Client)obj).numero ;else return false ;
}}
-
20
Association bidirectionnelle de 1 vers 1 en java
Benoît Charroux - De la conception à l’implémentation- Juillet 99 - 39
class Homme{Femme femme ;public Femme GetFemme(){
return femme ;}public void setFemme( Femme femme ){
this.femme = femme ;femme.homme = this ;
}}
class Femme{Homme homme ;public Homme GetHomme(){
return homme ;}public void setHomme( Homme homme ){
this.homme = homme ;homme.femme = this ;
}public static void main( String [] argv ){
Homme h = new Homme() ;Femme f = new Femme() ;h.setFemme( f ) ;
}}
• Les attributs de l’association peuvent être manipulés directement dans le même package, on peut les mettre à jour individuellement sans respecter la mise à jour simultanée des deux cotés de l’association.
Association bidirectionnelle de 1 vers plusieurs en java (1/4)
Benoît Charroux - De la conception à l’implémentation- Juillet 99 - 40
import java.util.Vector ;class Oeuvre{
�� ��� �2��������+������� �� ������// ...
}
public static void main( String [] argv ){Oeuvre donGiovani = new Oeuvre( "Don Govani" ) ;Exemplaire exp1 = new Exemplaire( 10 ) ;donGiovani.addExemplaire( exp1 ) ;
}
• Parcours de l’association dans le sens Œuvre -> Exemplaire :
class Exemplaire{3������������ // …
}
-
21
Association bidirectionnelle de 1 vers plusieurs en java (2/4)
Benoît Charroux - De la conception à l’implémentation- Juillet 99 - 41
• Implémentation de la classe Oeuvre
class Oeuvre{private String titre ;Vector exemplaires = new Vector() ; // association oeuvre / exemplairespublic void addExemplaire( Exemplaire exemplaire )throws ExemplaireDejaReferenceException{
if( exemplaires.contains( exemplaire ) == false ){// si l'exemplaire est déjà référencé ...exemplaires.addElement( exemplaire ) ; // on l’ajouteexemplaire.oeuvre = this ; // mise a jour du lien avec l’exemplaire
}else throw new ExemplaireDejaReferenceException( "Exemplaire deja present" ) ;
}public void removeExemplaire( Exemplaire exemplaire ) throws ExemplaireNonReferenceException{
if( exemplaires.removeElement( exemplaire ) == false )// si l'exemplaire est inconnuthrow new ExemplaireNonReferenceException( "Exemplaire inconnu" ) ;
else exemplaire.oeuvre = null ; // mise a jour du lien avec l'exemplaire }
}
Association bidirectionnelle de 1 vers plusieurs en java (3/4)
Benoît Charroux - De la conception à l’implémentation- Juillet 99 - 42
public static void main( String [] argv ){Oeuvre donGiovani = new Oeuvre( "Don Govani" ) ;Exemplaire exp1 = new Exemplaire( 10 ) ;exp1.addOeuvre( donGiovani ) ;
}
• Parcours de l’association dans le sens Exemplaire -> Œuvre :
-
22
Association bidirectionnelle de 1 vers plusieurs en java (4/4)
Benoît Charroux - De la conception à l’implémentation- Juillet 99 - 43
• Implémentation de la classe Exemplaire :
class Exemplaire{private int numero ;Oeuvre oeuvre ;public void addOeuvre( Oeuvre oeuvre ) throws ExemplaireDejaReferenceException{
if( oeuvre.exemplaires.contains( this ) == false ){// si l'exemplaire est déjà référencé ...oeuvre.exemplaires.addElement( this ) ; // on l’ajoutethis.oeuvre = oeuvre ; // mise a jour du lien exemplaire
}else throw new ExemplaireDejaReferenceException( "Exemplaire deja present" ) ;
}public void removeOeuvre( Oeuvre oeuvre )throws ExemplaireNonReferenceException{
if( oeuvre.exemplaires.removeElement( this ) == true ) this.oeuvre = null ; else throw new ExemplaireNonReferenceException( "Exemplaire inconnu" ) ;
}public boolean equals( Object obj ){
if( (obj!=null) && (obj instanceof Exemplaire) )return numero == ((Exemplaire)obj).numero ;else return false ;
}}
Association bidirectionnelle de 1 vers plusieurs en java (1/4)
Benoît Charroux - De la conception à l’implémentation- Juillet 99 - 44
• Modélisation d’une association bidirectionnelle par une classe d’association ;
• utilisation d’une table de hachage (hashtable) :
• un ensemble d’œuvres (vecteur) est accessible par un nom d’auteur (clef).
class Auteur{+���� �-�+4��;�� �� ������� -�+4��;�����
������;������ ��++�// ...
}
-
23
Association bidirectionnelle de 1 vers plusieurs en java (2/4)
Benoît Charroux - De la conception à l’implémentation- Juillet 99 - 45
class Auteur{private String nom ;static Hashtable dico = new Hashtable() ;public void addOeuvre( Oeuvre oeuvre ) throws OeuvreDejaPresentExecption{
Vector oeuvres ;oeuvres = (Vector)dico.remove( this ) ; // efface les œuvres pour pouvoir les modifierif( oeuvres == null ) // s’il n’y a pas d’œuvres ...
oeuvres = new Vector() ; // creation d’un vecteur d’oeuvresif( oeuvres.contains(oeuvre) == false ){ // si œuvre n’est pas presente ...
oeuvres.addElement( oeuvre ) ; // ajout de oeuvredico.put( this, oeuvres ) ; // mise a jour du dico
} else { // si œuvre est deja presente ...dico.put( this, oeuvres ) ; // on recre le dico a l’identiquethrow new OeuvreDejaPresentExecption( "Oeuvre deja presente" );
}}// ...
}
• Implémentation de la classe Auteur :
Association bidirectionnelle de 1 vers plusieurs en java (3/4)
Benoît Charroux - De la conception à l’implémentation- Juillet 99 - 46
class Auteur{// ...public void removeOeuvre( Oeuvre oeuvre ) throws OeuvreNonPresentExecption{
Vector oeuvres ;oeuvres = (Vector)dico.remove( this ) ; // on tente de recuperer les oeuvresif( oeuvres != null ){ // si les oeuvres existent
if( oeuvres.removeElement(oeuvre) == false ) // on tente d’effacer l’oeuvrethrow new OeuvreNonPresentExecption( "Oeuvre non presente" );
dico.put( this, oeuvres ) ; // on remet a jour le dictionnaire}else throw new OeuvreNonPresentExecption( "Oeuvre non presente" );
}}
• Implémentation de la classe Auteur :
-
24
Association bidirectionnelle de 1 vers plusieurs en java (4/4)
Benoît Charroux - De la conception à l’implémentation- Juillet 99 - 47
class Oeuvre{private String titre ;public Oeuvre( String titre ){
this.titre = titre ;}public void addAuteur( Auteur auteur ) throws AuteurDejaPresentExecption{
Vector oeuvres ;if( auteur.dico.containsKey(auteur) == false ){ // si l’auteur n’est pas present
oeuvres = new Vector() ; // on cre un vecteur d’oeuvresoeuvres.addElement( this ) ; // on y ajoute l’auteur courantauteur.dico.put( auteur, oeuvres ) ; // ajout dans le dico
} else {throw new AuteurDejaPresentExecption( "Auteur deja present" ) ;
}}public void removeAuteur( Auteur auteur ) throws AuteurNonPresentExecption{
if( auteur.dico.remove(auteur)==null )throw new AuteurNonPresentExecption( "Auteur deja present" ) ;
}
• Implémentation de la classe Oeuvre :