exercices
exercices
exercices
Définissez une classe Vehicule qui a pour attributs des informations valables pour tout type de
véhicule : sa marque , sa date d'achat, son prix d'achat et son prix courant.
Solution :
class Vehicule {
Définissez une méthode publique affiche() qui affiche la valeur des attributs.
Définissez deux classes Voiture et Avion, héritant de la classe Vehicule et ayant les attributs
supplémentaires suivants :
http://icwww.epfl.ch/~sam/ipo/series/serie07/solution_print.html 1/19
10/30/2016 Héritage et base du polymorphisme
class Avion extends Vehicule {
Définissez maintenant un constructeur pour Voiture, ainsi qu'une méthode affichant la valeur des
attributs.
Ces deux méthodes doivent, bien entendu, être publiques puisqu'elles sont précisément faites pour
être utilisées hors de la classe.
Notez que pour le constructeur de Voiture, on fait appel au constructeur de Vehicule . On fait
également appel à la méthode d'affichage de la superclasse dans la méthode affiche de Voiture.
public Avion(String marque, int date, double prix, String moteur, int heures) {
super(marque, date, prix);
this.moteur = moteur;
heuresVol = heures;
}
Les entêtes sont les mêmes pour Voiture et Avion que pour Vehicule, par contre les définitions
diffèrent.
http://icwww.epfl.ch/~sam/ipo/series/serie07/solution_print.html 2/19
10/30/2016 Héritage et base du polymorphisme
Voiture:
On se rend compte ici que l'on a besoin d'accèder à des attributs privés de la superclasse, ou de les
modifier (dateAchat, marque, prixAchat et prixCourant). Il faut donc enrichir la classe Vehicule des
"getters/setters" nécessaires :
Il aurait été possible de déclarer les attributs nécessaires comme protected dans la classe Vehicule
pour s'éviter la peine de définir les getters/setters. Ceci peut cependant nuire à une bonne
encapsulation : un autre programmeur peut hériter de votre classe Vehicule. Il aurait alors accès aux
détails d'implémentation et vous ne pourriez plus modifier librement cette implémentation sans
potentiellement causer du tort à ses programmes ! Voici enfin la méthode calculePrix pour les
avions :
http://icwww.epfl.ch/~sam/ipo/series/serie07/solution_print.html 3/19
10/30/2016 Héritage et base du polymorphisme
Pour finir, ceux qui le souhaitent peuvent trouver ici le code complet.
2. System.out.println(y.c)
Faux, car la classe de y (E2) ne dispose pas de la variable d'instance c qui est déclarée dans
une sousclasse (E3).
3. System.out.println(z.b)
Correct, car la variable d'instance b est héritée de la superclasse (E2) de z (qui est de type
E3).
4. System.out.println(v.e)
Faux, car la classe de v (E4) ne dispose pas de la variable d'instance e qui est déclarée dans
une classe parallèle (E3).
5. System.out.println(w.a)
Correct, car la variable d'instance a est héritée d'une superclasse (E1) de w (qui est de type
E5).
Direction.java
1
2
http://icwww.epfl.ch/~sam/ipo/series/serie07/solution_print.html 4/19
10/30/2016 Héritage et base du polymorphisme
3
4 class Direction
5 {
6 public static void main(String[] args) {
7 Ecole epfl = new Ecole(5);
8 epfl.add(new EtudiantRegulier("Gaston Peutimide", 2008, "SSC", 6.0));
9 epfl.add(new EtudiantRegulier("Yvan Rattrapeur", 2009, "SSC", 2.5));
10 epfl.add(new EtudiantEchange("Bjorn Borgue", 2010, "Informatique", "KTH"));
11 epfl.add(new Enseignant("Mathieu Matheu", 1998, "LMEP", 10000, "Physique"));
12 epfl.add(new Secretaire("Sophie Scribona", 1995, "LMT", 5000));
13 epfl.afficherStatistiques();
14 epfl.afficherEpfliens();
15 }
16
17 }
18
19
20 class Ecole {
21 private int nbEtudiants;
22 private int nbTotal;
23 private Epflien [] gens;
24
25 public final static int ANNEE = 2012;
26
public Ecole(int nbPersonnes) {
27
gens = new Epflien[nbPersonnes];
28
nbEtudiants = 0;
29
nbTotal = 0;
30
}
31
32
public void add(Epflien personne)
33
{
34 if (nbTotal < gens.length)
35 {
36 gens[nbTotal] = personne;
37 ++nbTotal;
38 if (personne.estEtudiant())
39 {
40 ++nbEtudiants;
41 }
42 }
43 }
44
45 public void afficherStatistiques() {
46 int nbAnneesTotal = 0;
47 for (int i = 0; i < gens.length; i++) {
48 nbAnneesTotal = nbAnneesTotal + (ANNEE ‐ gens[i].getAnnee());
49 }
50 System.out.println("Parmi les " + gens.length + " EPFLiens, " +
51 nbEtudiants + " sont des etudiants.");
52 double moyen = (double) nbAnneesTotal / gens.length;
53 System.out.println("Ils sont ici depuis en moyenne " + moyen + " ans");
54 }
55
public void afficherEpfliens() {
56
System.out.println("Liste des EPFLiens: ");
57
for (int i = 0; i < gens.length; i++)
58
gens[i].afficher();
59
}
60
}
61
62
63 class Epflien {
64 private String nom;
http://icwww.epfl.ch/~sam/ipo/series/serie07/solution_print.html 5/19
10/30/2016 Héritage et base du polymorphisme
125 super.afficher();
126 System.out.println(" Prope I : " + getPrope1());
127 }
128
129 public double getPrope1() {
130 return prope1;
131 }
132 }
133
134 class EtudiantEchange extends Etudiant {
135 private String uniOrigine;
136
public EtudiantEchange(String nom, int annee, String section, String uniOrigine) {
137
super(nom, annee, section);
138
this.uniOrigine = uniOrigine;
139
}
140
141 public void afficher() {
142 System.out.println("Etudiant d'echange:");
143 super.afficher();
144 System.out.println(" Uni d'origine : " + getUniOrigine());
145 }
146
147 public String getUniOrigine() {
148 return uniOrigine;
149 }
150 }
151
152 class Personnel extends Epflien {
153 private String labo;
154 private int salaire;
155
156 public Personnel(String nom, int annee, String labo, int salaire) {
157 super(nom, annee);
158 this.labo = labo;
159 this.salaire = salaire;
160 }
161
162 public void afficher() {
163 super.afficher();
164 System.out.println(" Laboratoire : " + getLabo());
165 System.out.println(" Salaire : " + getSalaire());
166 }
167
public String getLabo() {
168
return labo;
169
}
170
171 public int getSalaire() {
172 return salaire;
173 }
174 }
175
176 class Enseignant extends Personnel {
177 private String section;
178
179 public Enseignant(String nom, int annee, String labo, int salaire, String section) {
180 super(nom, annee, labo, salaire);
181 this.section = section;
182 }
183
184 public void afficher() {
185 System.out.println("Enseignant:");
186 super.afficher();
http://icwww.epfl.ch/~sam/ipo/series/serie07/solution_print.html 7/19
10/30/2016 Héritage et base du polymorphisme
186 super.afficher();
187 System.out.println(" Section d'enseignement : " + getSection());
188 }
189
190 public String getSection() {
191 return section;
192 }
193 }
194
195 class Secretaire extends Personnel {
196 public Secretaire(String nom, int annee, String labo, int salaire) {
197 super(nom, annee, labo, salaire);
198 }
199
public void afficher() {
200
System.out.println("Secretaire:");
201
super.afficher();
202
}
203 }
204
205
206
207
http://icwww.epfl.ch/~sam/ipo/series/serie07/solution_print.html 8/19
10/30/2016 Héritage et base du polymorphisme
Poste.java
1
2
3
4
5 /* Classe pour représenter le courrier
6 */
7
8 class Courrier {
9 // retourne le montant n'ecessaire pour affranchir le courrier
10 // en mode d'exp'edition normal
11
12 // on va faire une chose tre`s vilaine parcequ'on ne connait pas les
13 // m'ethodes abstraites : on va lui donner un corps arbitrairement
14 // d'efini (car on ne sait pas la d'efinir proprement
15 // a` ce niveau de la hi'erarchie
16 public double affranchirNormal(){return 0;};
17 // la bonne solution consiste a` d'eclarer cette m'ethode comme suit:
18 // abstract private double affranchirNormal();
19 // lorsque vous aurez vu le cours 8, expliquez pourquoi...
20
21 // les attributs (communs aux lettres et colis):
22 private double poids;
23 private boolean express;
24 private String adresse;
25
26 // un constructeur possible pour la classe
27 public Courrier(double poids, boolean express, String adresse) {
28 this.poids = poids;
29 this.express = express;
30 this.adresse = adresse;
}
31
32
// un getter pour le poids (car utile dans les sousclasse)
33
public double getPoids() {
34
return poids;
35
}
36
37 // retourne le montant n'ecessaire pour affranchir le courrier.
38 // elle appelle affranchirNormal et retourne le double de ce montant
39 // si le mode d'exp'edition est express ('eviter la duplication du code
40 // qui double le montant dans les m'ethodes affranchirnormal
41 // des sousclasses)
42 public double affranchir() {
43 if (! valide())
44 {
45 return 0;
46 }
47 else
48 {
49 double total = affranchirNormal();
50 if (express) {
51 total *= 2;
52 }
53 return total;
http://icwww.epfl.ch/~sam/ipo/series/serie07/solution_print.html 9/19
10/30/2016 Héritage et base du polymorphisme
54 }
55 }
56
57 // un courrier est invalide si l'adresse de destination est vide
58 // methode utilis'ee par Boite::affranchir et
59 // Boite::courriersInvalides
60 public boolean valide() {
61 return adresse.length() > 0;
62 }
63
64 @Override
65 public String toString() {
66 String s = "";
67 if (!valide())
68 {
s+= "(Courrier invalide)\n";
69
}
70
s+= " Poids : " + poids + " grammes\n";
71
s+= " Express : " + (express ? "oui" : "non") + "\n";
72
s+= " Destination : " + adresse + "\n";
73
s+= " Prix : " + affranchir() + " CHF\n";
74
return s;
75
}
76
77 }
78
79 /* Une classe pour repr'esenter les lettres
80 */
81
82 class Lettre extends Courrier {
83
84 //attributs sp'ecifiques aux lettres:
85 private String format = "";
86
87 public Lettre(double poids, boolean express, String adresse, String format){
88 super(poids, express, adresse);
89 this.format = format;
90 }
91
92 // red'efinit affranchirNormal()
93 public double affranchirNormal() {
94 double montant = 0;
95 if (format.equals("A4")){
96 montant = 2.0;
97 } else {
98 montant = 3.5;
99 }
100 montant += getPoids()/1000.0;
101 return montant;
102 }
103
104 // inutile de red'efinir la méthode valide() pour les lettres
105
106 @Override
public String toString() {
107
String s = "Lettre\n";
108
s += super.toString();
109
s += " Format : " + format + "\n";
110
return s;
111
}
112
113 }
114 /* Une classe pour repr'esenter les publicit'es
http://icwww.epfl.ch/~sam/ipo/series/serie07/solution_print.html 10/19
10/30/2016 Héritage et base du polymorphisme
115 */
116
117 class Publicite extends Courrier {
118
119 public Publicite(double poids, boolean express, String adresse){
120 super(poids, express, adresse);
121 }
122
123 // redéfinit affranchirNormal()
124 public double affranchirNormal() {
125 return getPoids()/1000.0 * 5.0;
126 }
127
128
// inutile de red'efinir la méthode valide() pour les publicités
129
130
@Override
131
public String toString() {
132
String s = "Publicité\n";
133
s += super.toString();
134 return s;
135 }
136
137 }
138
139 /* Une classe pour repr'esenter les colis
140 */
141 class Colis extends Courrier {
142
143 //attributs sp'ecifiques aux colis:
144 private double volume;
145
146 public Colis(double poids, boolean express, String adresse, double volume) {
147 super(poids, express, adresse);
148 this.volume = volume;
149 }
150
151 // redéfinit affranchirNormal();
152 public double affranchirNormal() {
153 // affranchit les colis selon une formule pr'ecise
154 return 0.25 * volume + getPoids()/1000.0;
155 }
156
157 // ici il faut red'efinir (sp'ecialiser) la re`gle de validit'e des colis
158 // un colis est invalide s' il a une mauvaise adresse
159 //ou depasse un certain volume
160 public boolean valide(){
161 return (super.valide() && volume <= 50);
162 }
163
@Override
164
public String toString() {
165
String s = "Colis\n";
166
s += super.toString();
167
s += " Volume : " + volume + " litres\n";
168
return s;
169
}
170
171
172 }
173
174 /* Une classe pour repr'esenter la boite aux lettre
175 */
http://icwww.epfl.ch/~sam/ipo/series/serie07/solution_print.html 11/19
10/30/2016 Héritage et base du polymorphisme
176
177 class Boite {
178
179 private Courrier[] contenu;
180 private int index;
181
182 // constructeur
183 public Boite(int max) {
184 contenu = new Courrier[max];
185 index = 0;
186 }
187
188 // la méthode demand'ee
189 public double affranchir() {
190 double montant = 0.0;
191 for(int i=0; i < index; ++i){
192 Courrier c = contenu[i];
193 montant += c.affranchir();
}
194
return montant;
195
}
196
197 public int size() {
198 return index;
199 }
200
201 public Courrier getCourrier(int index) {
202 if (index < contenu.length)
203 return contenu[index];
204 else
205 return null;
206 }
207
208 // autre m'ethode demandée dans l'interface
209 // d'utilisation de la classe
210 public int courriersInvalides() {
211 int count = 0;
212 for (int i = 0; i < index; i++) {
213 if (!contenu[i].valide())
214 count++;
215 }
216 return count;
217 }
218
219 // difficile de fonctionner sans
220 public void ajouterCourrier(Courrier unCourrier) {
221 if (index < contenu.length){
222 contenu[index] = unCourrier;
223 index++;
224 } else {
225 System.out.println("Impossible d'ajouter un nouveau courrier. Boite pleine !");
226 }
227 }
228
public void afficher() {
229
for (int i = 0; i < index; i++) {
230
System.out.println(contenu[i]);
231
}
232
}
233
234 }
235
236
// PROGRAMME PRINCIPAL (non demandé)
http://icwww.epfl.ch/~sam/ipo/series/serie07/solution_print.html 12/19
10/30/2016 Héritage et base du polymorphisme
237 // PROGRAMME PRINCIPAL (non demandé)
238 class Poste {
239
240 public static void main(String args[]) {
241 //Cr'eation d'une boiteauxlettres
242 Boite boite = new Boite(30);
243
244 //Creation de divers courriers/colis..
245 Lettre lettre1 = new Lettre(200, true, "Chemin des Acacias 28, 1009 Pully", "A3");
246 Lettre lettre2 = new Lettre(800, false, "", "A4"); // invalide
247
248 Publicite pub1 = new Publicite(1500, true, "Les Moilles 13A, 1913 Saillon");
249 Publicite pub2 = new Publicite(3000, false, ""); // invalide
250
251 Colis colis1 = new Colis(5000, true, "Grand rue 18, 1950 Sion", 30);
252 Colis colis2 = new Colis(3000, true, "Chemin des fleurs 48, 2800 Delemont", 70); //Colis invalide !
253
254 boite.ajouterCourrier(lettre1);
255 boite.ajouterCourrier(lettre2);
boite.ajouterCourrier(pub1);
256
boite.ajouterCourrier(pub2);
257
boite.ajouterCourrier(colis1);
258 boite.ajouterCourrier(colis2);
259
260
261 System.out.println("Le montant total d'affranchissement est de " +
262 boite.affranchir());
263 boite.afficher();
264
265 System.out.println("La boite contient " + boite.courriersInvalides()
266 + " courriers invalides");
267 }
268 }
269
270
271
272
Puissance4.java
1
2
3
4
5
6 import java.util.Scanner;
7 /**
8 * Classe principale
9 */
10 class Puissance4 {
11 protected static Scanner scanner = new Scanner(System.in);
12 public static void main(String[] args) {
13 System.out.println("Entrez votre nom: ");
14 String nom = scanner.nextLine();
15 System.out.println("");
77 initJeu(8);
78 }
79
80 private void initJeu(int taille) {
81 this.taille = taille;
82 grille = new int[taille][taille];
83 for (int col = 0; col < taille ; col++) {
84 for (int row = 0; row < taille; row++) {
85 grille[col][row] = VIDE;
86 }
87 }
88 }
89
public boolean joueCoup(int col, int joueur) {
90
if ((col < 0) || (col >= taille)) {
91
return false;
92
}
93
94 // Trouve la première place vide dans la colonne
95 for (int ligne = 0; ligne < taille; ligne++) {
96 if (grille[col][ligne] == VIDE) {
97 grille[col][ligne] = joueur;
98 return true;
99 }
100 }
101
102 // La colonne est pleine
103 return false;
104 }
105
106 /**
107 * Cette méthode vérifie toutes les lignes, colonnes et diagonales pour une série de 4 pions
108 * de la même couleur. Si une telle série existe, retourne true.
109 *
110 * Notez qu'il n'est pas nécessaire de retourner la couleur des 4 pions alignés,
111 * puisqu'il s'agit de celle de celui qui vient de jouer.
112 * @return true si le jeu contient 4 pions alignés
113 */
114 public boolean cherche4() {
115 // Vérifie les horizontales ( )
116 for (int ligne = 0; ligne < taille; ligne++) {
117 if (cherche4alignes(0, ligne, 1, 0)) {
118 return true;
119 }
120 }
121
122 // Vérifie les verticales ( ¦ )
123 for (int col = 0; col < taille; col++) {
124 if (cherche4alignes(col, 0, 0, 1)) {
125 return true;
126 }
127 }
128
129 // Diagonales (cherche depuis la ligne du bas)
130 for (int col = 0; col < taille; col++) {
131 // Première diagonale ( / )
132 if (cherche4alignes(col, 0, 1, 1)) {
133 return true;
134 }
// Deuxième diagonale ( \ )
135
if (cherche4alignes(col, 0, ‐1, 1)) {
136
return true;
137
138 }
http://icwww.epfl.ch/~sam/ipo/series/serie07/solution_print.html 15/19
10/30/2016 Héritage et base du polymorphisme
138 }
139 }
140
141 // Diagonales (cherche depuis les colonnes gauches et droites)
142 for (int ligne = 0; ligne < taille; ligne++) {
143 // Première diagonale ( / )
144 if (cherche4alignes(0, ligne, 1, 1)) {
145 return true;
146 }
147 // Deuxième diagonale ( \ )
148 if (cherche4alignes(taille ‐ 1, ligne, ‐1, 1)) {
149 return true;
150 }
151 }
152
// On n'a rien trouvé
153
return false;
154
}
155
156
/**
157
* Cette méthode cherche 4 pions alignés sur une ligne. Cette ligne est définie par
158
* le point de départ, ou origine de coordonnées (oCol,oLigne), et par le déplacement
159
* delta (dCol,dLigne). En utilisant des valeurs appropriées pour dCol et dLigne
160
* on peut vérifier toutes les directions:
161
* horizontale: dCol = 0, dLigne = 1
162
* vérticale: dCol = 1, dLigne = 0
163
* 1ère diagonale: dCol = 1, dLigne = 1
164
* 2ème diagonale: dCol = 1, dLigne = 1
165
*
166
* @param oCol Colonne d'origine de la recherche
167
* @param oLigne Ligne d'origine de la recherche
168
* @param dCol Delta de déplacement sur une colonne
169
* @param dLigne Delta de déplacement sur une ligne
170
* @return true si on trouve un alignement
171
*/
172
private boolean cherche4alignes(int oCol, int oLigne, int dCol, int dLigne) {
173
int couleur = VIDE;
174
int compteur = 0;
175
176 int curCol = oCol;
177 int curRow = oLigne;
178
179 while ((curCol >= 0) && (curCol < taille) && (curRow >= 0) && (curRow < taille)) {
180 if (grille[curRow][curCol] != couleur) {
181 // Si la couleur change, on réinitialise le compteur
182 couleur = grille[curRow][curCol];
183 compteur = 1;
184 } else {
185 // Sinon on l'incrémente
186 compteur++;
187 }
188
189 // On sort lorsque le compteur atteint 4
190 if ((couleur != VIDE) && (compteur == 4)) {
191 return true;
192 }
193
194 // On passe à l'itération suivante
195 curCol += dCol;
196 curRow += dLigne;
197 }
198
199 // Aucun alignement n'a été trouvé
http://icwww.epfl.ch/~sam/ipo/series/serie07/solution_print.html 16/19
10/30/2016 Héritage et base du polymorphisme
320
http://icwww.epfl.ch/~sam/ipo/series/serie07/solution_print.html 18/19
10/30/2016 Héritage et base du polymorphisme
320
321
http://icwww.epfl.ch/~sam/ipo/series/serie07/solution_print.html 19/19