-
Dans un premier temps, on cherche à définir un Container.
Un conteneur possède une destination sous forme de chaîne de caractères ainsi qu'un poids
(weight en Anglais) qui est une valeur entière.
Il ne doit pas être possible de créer un conteneur avec des valeurs invalides: la destination doit exister
et le poids doit être positif ou nul.
Écrire le type Container de telle façon à ce que le code suivant fonctionne:
public static void main(String[] args) {
var container = new Container("Germany", 500);
System.out.println(container.destination()); // Germany
System.out.println(container.weight()); // 500
}
-
On veut maintenant introduire la notion de Manifest, un manifeste contient une liste de conteneurs.
Pour l'instant, un manifeste définit une seule méthode add(conteneur) qui permet d'ajouter
un conteneur au manifeste.
Il ne doit pas être possible d'ajouter un conteneur null.
Écrire le type Manifest tel que le code suivant fonctionne:
public static void main(String[] args) {
...
var container2 = new Container("Italy", 400);
var container3 = new Container("Austria", 200);
var manifest = new Manifest();
manifest.add(container2);
manifest.add(container3);
System.out.println(manifest.weight()); // 600
}
-
On souhaite maintenant pouvoir afficher un manifeste.
Afficher un manifeste revient à afficher chaque conteneur sur une ligne,
avec un numéro, 1 pour le premier conteneur, 2 pour le suivant, etc, suivi
de la destination du conteneur ainsi que de son poids.
Le formatage exact pour une ligne est:
[numéro]. [destination] [poids]kg
suivi d'un retour à la ligne (y compris après la dernière ligne).
Modifier le type Manifest pour que le code suivant ait le comportement attendu:
public static void main(String[] args) {
...
var container4 = new Container("Spain", 250);
var container5 = new Container("Swiss", 200);
var manifest2 = new Manifest();
manifest2.add(container4);
manifest2.add(container5);
System.out.println(manifest2);
// 1. Spain 250kg
// 2. Swiss 200kg
}
-
Un porte conteneur comme son nom ne l'indique pas peut aussi transporter des passagers.
Un Passenger est défini par une destination uniquement, les passagers ne sont pas assez
lourd pour avoir un vrai poids.
Dans un premier temps, comment définir un Passenger tel que l'on puisse créer un passager uniquement
avec sa destination. Puis expliquer comment modifier Manifest pour que l'on puisse enregistrer
aussi bien des conteneurs que des passagers.
Pour l'affichage, un passager affiche la destination ainsi que "(passenger)" entre parenthèse
(cf le code plus bas).
Ecrire le code de Passenger et modifier le code de Manifest tel que le code
ci-dessous fonctionne.
public static void main(String[] args) {
...
var passenger1 = new Passenger("France");
var container6 = new Container("England", 350);
var manifest3 = new Manifest();
manifest3.add(passenger1);
manifest3.add(container6);
System.out.println(manifest3);
// 1. France (passenger)
// 2. England 350kg
-
On souhaite ajouter une méthode price à Manifest qui calcul le prix
pour qu'un conteneur ou qu'un passager soit sur le bateau.
-
Le prix pour un passager est 10.
-
Le prix pour un conteneur est le poid du conteneur multiplié par 2.
Ajouter une méthode price à Manifest et faite en sorte que le prix
soit calculés correctement.
System.out.println(manifest3.price()); // 710
-
Il arrive que l'on soit obligé de décharger tous les conteneurs liés à une destination
s'il y a des problèmes d'embargo (quand un dictateur se dit qu'il s'offirait bien une partie
d'un pays voisin par exemple). Dans ce cas, il faut aussi supprimer tous les conteneurs
liés à cette destination au niveau du manifeste (mais pas les passagers).
Pour prendre en compte cela, on introduit une méthode removeAllContainersFrom(destination)
qui supprime tous les conteneurs liés à une destination. S'il n'y a pas de conteneur pour cette
destination, on ne fait rien.
Modifier le code pour introduire cette méthode pour que l'exemple ci-dessous fonctionne:
Note: pour savoir si il s'agit d'un conteneur ou pas, on pourrait introduire une méthode isContainer
dont l'implantation par défaut sera de retourner false.
public static void main(String[] args) {
...
var container8 = new Container("Russia", 450);
var container9 = new Container("China", 200);
var container10 = new Container("Russia", 125);
var passenger2 = new Passenger("Russia");
var manifest4 = new Manifest();
manifest4.add(container8);
manifest4.add(container9);
manifest4.add(container10);
manifest4.add(passenger2);
manifest4.removeAllContainersFrom("Russia");
System.out.println(manifest4);
// 1. China 200kg
// 2. Russia (passenger)
-
Pour résoudre la question précédente, au lieu de faire des appels de méthode,
on peut aussi utiliser instanceof. Expliquer comment on peut utiliser instanceof.
Puis expliquer selon vous quel est le problème d'utiliser
instanceof dans ce contexte et pourquoi on ne doit pas l'utiliser.
-
Question optionnelle:
On met les conteneurs ayant la même destination au même endroit sur le porte-conteneur, et si
un porte-conteneur est mal équilibré il a une fâcheuse tendance à se retourner. Donc, pour aider au placement
des conteneurs, il doit être possible de fournir un dictionnaire qui, pour chaque destination, indique
le poids de l'ensemble des conteneurs liés à cette destination.
Pour cela, écrire une méthode weightPerDestination qui, pour un manifeste donné, renvoie un dictionnaire
qui indique le poids des conteneurs pour chaque destination.
Par exemple, avec le code ci-dessous, il y a deux conteneurs qui ont comme destination "Monaco", avec un
poids combiné de 100 + 300 = 400, tandis que "Luxembourg" a un seul conteneur de poids 200.
public static void main(String[] args) {
...
var container11 = new Container("Monaco", 100);
var container12 = new Container("Luxembourg", 200);
var container13 = new Container("Monaco", 300);
var passenger3 = new Passenger("Paris");
var manifest8 = new Manifest();
manifest8.add(container11);
manifest8.add(container12);
manifest8.add(container13);
manifest8.add(passenger3);
System.out.println(manifest8.weightPerDestination());
// {Monaco=400, Paris=0, Luxembourg=200}
}