TD Java Héritage Et Polymorphisme

Télécharger au format docx, pdf ou txt
Télécharger au format docx, pdf ou txt
Vous êtes sur la page 1sur 7

TD/TP Java Héritage et polymorphisme

Exercice 60 : définition d’une classe dérivée, droits d’accès

On dispose de la classe suivante :


class Point
{ public void initialise (int x, int y) { this.x = x ; this.y = y ; }
public void deplace (int dx, int dy) { x += dx ; y += dy ; }
public int getX() { return x ; }
public int getY() { return y ; }
private int x, y ;
}
Réaliser une classe PointA, dérivée de Point disposant d’une méthode affiche affichant (en fenêtre
console) les coordonnées d’un point. Ecrire un petit programme utilisant les deux classes Point et
PointA.
Que se passerait-il si la classe Point ne disposait pas des méthodes getX et getY ?

Exercice 61 : description d’une classe dérivée

On dispose de la classe suivante :

class Point
{public void setPoint(intx,inty) {this.x=x;this.y=y;}
public void deplace (int dx, int dy) { x += dx ; y += dy ; }
public void affCoord ()
{ System.out.println ("Coordonnees : " + x + " " + y) ;
}
private int x, y ;
}
Réaliser une classe PointNom, dérivée de Point permettant de manipuler des points définis par deux
coordonnées (int) et un nom (caractère). On y prévoira les méthodes suivantes :

• setPointNom pour définir les coordonnées et le nom d’un objet de type PointNom,

• setNom pour définir seulement le nom d’un tel objet,

• affCoordNom pour afficher les coordonnées et le nom d’un objet de type PointNom. Écrire un petit
programme utilisant la classe PointNom.

 Nous définissons une classe dérivée en utilisant le mot clé extends :

class PointNom extends Point

Dans cette classe PointNom, nous introduisons un champ (de préférence privé) destiné à
contenir le nom du point :
private char nom ;

La méthode setNom est triviale. Compte tenu de l’encapsulation des données de Point, nos deux autres
méthodes doivent absolument recourir aux méthodes publiques de Point.

Exercice 62 : Héritage et appels de constructeur

On dispose de la classe suivante (disposant cette fois d’un constructeur) :

class Point
{
publicPoint(intx,inty) {this.x=x;this.y=y;}
public void affCoord()
{ System.out.println ("Coordonnees : " + x + " " + y) ; }
private int x, y ;
}
Réaliser une classe PointNom, dérivée de Point permettant de manipuler des points définis par leurs
coordonnées (entières) et un nom (caractère). On y prévoira les méthodes suivantes :

• constructeur pour définir les coordonnées et le nom d’un objet de type PointNom,

• affCoordNom pour afficher les coordonnées et le nom d’un objet de type PointNom.

Écrire un petit programme utilisant la classe PointNom.

• Cet exercice est voisin de l’exercice 61 mais, cette fois, les deux classes disposent d’un
constructeur. Celui de la classe dérivée PointNom doit prendre en charge la construction de
l’intégralité de l’objet correspondant, quitte à s’appuyer pour cela sur le constructeur de la
classe de base (ce qui est indispensable ici puisque la classe Point ne dispose pas de méthodes
d’accès). Rappelons que l’appel du constructeur de la classe de base (fait à l’aide du mot clé
super) doit constituer la première instruction du constructeur de la classe dérivée.

Exercice 63 : redéfinition

On dispose de la classe suivante :

class Point
{ publicPoint(intx,inty) {this.x=x;this.y=y;}
public void affiche()
{ System.out.println ("Coordonnees : " + x + " " + y) ; }
private int x, y ;
}
Réaliser une classe PointNom, dérivée de Point permettant de manipuler des points définis par leurs
coordonnées et un nom (caractère). On y prévoira les méthodes suivantes :

• constructeur pour définir les coordonnées et le nom d’un objet de type PointNom,

• affiche pour afficher les coordonnées et le nom d’un objet de type PointNom.
• Cet exercice est voisin de l’exercice 62. L’écriture du constructeur reste la même. Mais, cette
fois, on doit redéfinir la méthode affiche dans la classe dérivée. L’affichage du nom n’y pose
aucun problème :
• System.out.print ("Point de nom " + nom + " ") ;
• En revanche, il nous faut faire appel à la méthode affiche de la classe de base. Pour ce faire,
nous employons le mot clé super :
• super.affiche() ;

Exercice 64 : construction et initialisation d’une classe dérivée

Quels résultats fournit ce programme ?

class A {
public A (int nn)
{ System.out.println ("Entree Constr A - n=" + n + " p=" + p) ;
n = nn ;
System.out.println ("Sortie Constr A - n=" + n + " p=" + p) ;
}
public int n ; // ici, exceptionnellement, pas d'encapsulation
public int p=10 ;
}
class B extends A
{ public B (int n, int pp)
{ super (n) ;
System.out.println ("Entree Constr B - n=" + n + " p=" + p + " q=" + q) ;
p = pp ;
q = 2*n ;
System.out.println ("Sortie Constr B - n=" + n + " p=" + p + " q=" + q) ;
}
public int q=25 ;
}
public class TstInit
{ public static void main (String args[])
{ A a = new A(5) ;
B b = new B(5, 3) ;
}
}
Il faut tenir compte de l’ordre dans lequel ont lieu les initialisations des champs (explicite et implicite)
et les appels des constructeurs, à savoir :

 initialisation par défaut des champs de l’objet dérivé (y compris ceux hérités),
 initialisation explicite des champs hérités,
 exécution du constructeur de la classe de base,
 initialisation explicite des champs spécifiques à l’objet dérivé,
 exécution du constructeur de la classe dérivée.

Exercice 67 : les bases du polymorphisme

Quels résultats fournit le programme suivant ?

class A
{ public void affiche() { System.out.print ("Je suis un A ") ; }
}
class B extends A {}
class C extends A
{ public void affiche() { System.out.print ("Je suis un C ") ; }
}
class D extends C{
public void affiche()
{ System.out.print ("Je suis un D ") ; }
}
class E extends B {}
class F extends C {}

public class Poly


{ public static void main (String arg[])
{ A a = new A(); a.affiche(); System.out.println();
B b = new B(); b.affiche();
a=b; a.affiche(); System.out.println();

C c = new C(); c.affiche();


a=c; a.affiche(); System.out.println();

D d = new D(); d.affiche();


a=d; a.affiche();
c=d; c.affiche(); System.out.println();

E e = new E(); e.affiche();


a=e; a.affiche();
b=e; b.affiche(); System.out.println();

F f = new F(); f.affiche();


a=f; a.affiche();
c=f; c.affiche();
}
}
Certaines possibilités d’affectation entre objets des types classes A, B, C, D, E et F ne figurent pas
dans le programme ci-dessus. Pourquoi ?

En Java, l’une des propriétés du "polymorphisme" est que l’appel d’une méthode est déterminé au
moment de l’exécution, suivant la nature de l’objet effectivement référencé (et non seulement suivant
le type de la référence). C’est pourquoi ici tous les appels de affiche concernant un même objet
fournissent le même message, quel que soit le type de référence utilisé.

Exercice 69 : les limites du polymorphisme

Soit les classes Point et PointNom ainsi définies :

class Point
{ public Point (int x, int y) { this.x = x ; this.y = y ; }
public static boolean identiques (Point a, Point b)
{ return ( (a.x==b.x) && (a.y==b.y) ) ; }
public boolean identique (Point a)
{ return ( (a.x==x) && (a.y==y) ) ; }
private int x, y ;
}
class PointNom extends Point
{ PointNom (int x, int y, char nom)
{ super (x, y) ; this.nom = nom ; }
private char nom ;
}
1. Quels résultats fournit ce programme ? Expliciter les conversions mises en jeu et les règles utilisées
pour traiter les différents appels de méthodes :

public class LimPoly


{ public static void main (String args[])
{ Point p = new Point (2, 4) ;
PointNom pn1 = new PointNom (2, 4, 'A') ;
PointNom pn2 = new PointNom (2, 4, 'B') ;
System.out.println (pn1.identique(pn2)) ;
System.out.println (p.identique(pn1)) ;
System.out.println (pn1.identique(p)) ;
System.out.println (Point.identiques(pn1, pn2)) ;
}
}
2. Doter la classe PointNom d’une méthode statique identiques et d’une méthode identique fournissant
toutes les deux la valeur true lorsque les deux points concernés ont à la fois mêmes coordonnées et
même nom. Quels résultats fournira alors le programme précédent ? Quelles seront les conversions
mises en jeu et les règles utilisées ?

Exercice 70 : classe abstraite

On souhaite disposer d’une hiérarchie de classes permettant de manipuler des figures géométriques.
On veut qu’il soit toujours possible d’étendre la hiérarchie en dérivant de nouvelles classes mais on
souhaite pouvoir imposer que ces dernières disposent toujours des méthodes suivantes :

• void affiche ()

• void homothetie (double coeff)

• void rotation (double angle)

Écrire la classe abstraite Figure qui pourra servir de classe de base à toutes ces classes.

• Il suffit d’appliquer les règles de définition d’une classe abstraite. On y place les en-têtes des
méthodes qu’on souhaite voir redéfinies dans les classes dérivées, en leur associant le mot clé
abstract.

Exercice 71 : classe abstraite et polymorphisme

Compléter la classe abstraite Figure de l’exercice précédent, de façon qu’elle implémente :

• une méthode homoRot (double coef, double angle) qui applique à la fois une homothétie et une
rotation à la figure,

• de méthodes statiques afficheFigures, homothetieFigures et rotationFigures appliquant une même


opération (affichage, homothétie ou rotation) à un tableau de figures (objets d’une classe
dérivée de Figure).

• Une classe abstraite peut comporter des définitions de méthodes (non abstraites) qui pourront
alors être utilisées par les classes dérivées sans qu’il ne soit nécessaire de les redéfinir (mais on
peut toujours le faire !). D’autre part, une classe abstraite peut comporter des méthodes
statiques, pour peu que celles-ci ne soient pas abstraites (ce qui n’aurait aucune signification).

Exercice 72 : interface

On souhaite disposer de classes permettant de manipuler des figures géométriques. On souhaite


pouvoir caractériser celles qui possèdent certaines fonctionnalités en leur demandant d’implémenter
des interfaces, à savoir :

• Affichable pour celles qui disposeront d’une méthode void affiche (),

• Tranformable pour celles qui disposeront des deux méthodes suivantes :

void homothetie (double coeff)

void rotation (double angle)

• Écrire les deux interfaces Affichable et Transformable.


• Il suffit d’appliquer les règles de définition d’une interface.

Exercice 73 : comparaison entre héritage et objet membre

On dispose de la classe suivante :

class Point
{ public Point (double x, double y) { this.x=x ; this.y=y ; }
public void deplace (double dx, double dy) { x+=dx ; y+=dy ; }
public void affiche ()
{ System.out.println ("Point de coordonnees " + x + " " + y) ; }
public double getX() { return x ; }
public double getY() { return y ; }
private double x, y ;
}

On souhaite réaliser une classe Cercle disposant des méthodes suivantes :

 constructeur recevant en argument les coordonnées du centre du cercle et son rayon,


 deplaceCentre pour modifier les coordonnées du centre du cercle,
 changeRayon pour modifier le rayon du cercle,
 getCentre qui fournit en résultat un objet de type Point correspondant au centre du cercle,
 affiche qui affiche les coordonnées du centre du cercle et son rayon.
1. Définir la classe Cercle comme classe dérivée de Point.
2. Définir la classe Cercle comme possédant un membre de type Point.

Dans les deux cas, on écrira un petit programme mettant en jeu les différentes fonctionnalités de la
classe Cercle.

Vous aimerez peut-être aussi