Licence Science-Technologie-Santé - mention Informatique - 3e année module Programmation Objet Avancée
Examen – 03/09/2009 – 1h
Les polycopiés de cours et notes de TD et de TP sont autorisés
Problème A
On dispose de deux classes implémentant chacune une méthode d'affichage graphique nommée affichage. La classe C1 implémente la méthode avec du code C natif compilé pour Linux (Java offre la possibilité d'appeler à partir de code Java des méthodes écrites en C dans une librairie). La classe C2 implémente la méthode en Java. Sous Linux, il est donc plus avantageux d'utiliser la méthode implémentée par C1 (car la méthode est plus rapide à l'exécution) et sous Windows, on ne peut utiliser que la méthode implémentée par C2.
public interface IAffichage{
public void affichage();
}
public class C1 implements IAffichage { public native void affichage();
...
}
public class C2 implements IAffichage { public void affichage(){...}
...
}
Question 1 :
Sans modifier les classes et interface existantes, et en utilisant un patron de conception, écrire une classe permettant de choisir, à l'exécution, d'utiliser l'une ou l'autre méthode en fonction du système d'exploitation. Préciser quel patron est utilisé, et comment.
Ecrire une méthode main qui fait exécuter l'une ou l'autre méthode en fonction du système d'exploitation. Pour tester le système d'exploitation sur lequel tourne la machine virtuelle, on peut utiliser la méthode System.getProperty("os.name") qui renvoie le nom du système (''Linux'' ou ''Windows'' par exemple).
Question 2 :
Sans modifier les classes et interfaces existantes, écrire si possible une méthode générique permettant de choisir à l'exécution d'utiliser la méthode affichage de C1 ou C2 en fonction du système d'exploitation. Si cela se révèle impossible, expliquer pourquoi.
Correction
Question 1 : on utilise le patron Strategy. La classe va utiliser par composition une instance de l'interface IAffichage, et la méthode d'affichage sera appelée sur cette instance.
public class Solution{
private IAffichage ia;
public Solution(IAffichage ia){this.ia= ia;}
public void setAffichage(IAffichage ia){this.ia=ia;}
public void monAffichage(){ia.affichage();}
public static void main(String[] truc){
Solution s = new Solution(new C1());
if(System.getProperty("os.name").equals("Windows")) s.setAffichage(new C2());
s.monAffichage();
} }
Question 2 : on voudrait écrire une méthode générique comme suit :
public <T extends IAffichage> void monAffichage(){
T temp = new T();
temp.affichage();
}
Mais il est impossible d'instancier un type générique. Il faudrait pour pouvoir utiliser un type générique que la méthode affichage soit statique, mais il n'est pas possible de déclarer une méthode statique dans une interface. Il n'est donc pas possible d'utiliser la généricité pour régler le problème posé.