Première partie
Objectifs d'apprentissage
- Appliquer le concept d'héritage pour concevoir une application.
- Concevoir une classe qui réalise une interface.
1 - Héritage et polymorphisme
- Une classe (enfant) est dite dérivée d'une autre si elle hérite de cette classe (mère).
- Le mot clé extends est utilisé pour signifier qu'une classe hérite de la classe spécifiée.
- Lorsqu'une classe est dérivée d'une autre, elle peut accéder toutes les méthodes ou variables d'instance déclarées public ou protected.
Le mot polymorphisme provient de « poly » qui signifie « plusieurs » et « morphes » qui signifie « formes ». En Java, le polymorphisme signifie qu'une instance d'une classe (un objet) peut être utilisée comme si elle avait plusieurs types, ayant ainsi de nombreux comportements. Par plusieurs types, on entend ici qu'elle dérive d'une autre classe ou d'autres interfaces.
2 - Les interfaces
Vous pouvez utiliser les interfaces en Java afin de démontrer le principe de polymorphisme.
public interface GreetingsInterface{
// An interface cannot contain an implementation
// of the method, only the signature.
public void sayGreetings();
}
Vous pouvez déclarer des constantes (static et final) dans une interface, mais en général, il ne s'agit pas d'une pratique recommandée. Nous essayons plutôt d'éviter de mettre des constantes dans les interfaces.
Les méthodes doivent être implémentées par les classes avant qu'il soit possible de les accéder. Notez que toutes les méthodes d'une interface sont publiques, et ce, même si vous omettez de mettre le mot clé « public ».
Pour faire usage d'une interface, vous devez implémenter (« implement ») cette dernière dans une classe Java.
// The key word implements signals to the compiler
// that the SpanishGreetings class implements the
// GreetingsInterface interface
public class SpanishGreetings implements GreetingsInterface{
// A class that implements an interface must implement
// all the methods declared in the interface
public void sayGreetings() {
// The class does not need to implement (declare)
// the variables of an interfaceWhat gets printed to the console after executing the method main?
System.out.println("Hola");
}
}
public class JapaneseGreetings implements GreetingsInterface{
public void sayGreetings() {
System.out.println(“Konnichiwa”);
}
}
Lorsqu'une classe réalise une interface, vous pouvez déclarer une variable référence dont le type est nom de l'interface (une variable référence dont le type est le nom de l'interface désigne un objet dont la classe réalise cette interface). Voici un exemple d'une méthode main :
public static void main(String[] args){
// The variable is declared of interface type GreetingsInterface,
// the object created is of type SpanishGreetings.
GreetingsInterface myGreetings;
myGreetings = new SpanishGreetings();
myGreetings.sayGreetings();
// The variable is declared of interface type GreetingsInterface,
// the object created is of type JapaneseGreetings.
myGreetings = new JapaneseGreetings();
myGreetings.sayGreetings();
}
Question 2.1 :
Qu'est-ce qui sera imprimé sur la console lors de l'exécution de la méthode main?
RéponseSi on omet d'implémenter une méthode faisant partie de l'interface, nous obtiendrons un message d'erreur. Repronons l'exemple ci-haut, mais cettre fois SpanishGreetings n'implémente pas la méthode sayGreetings().
public class SpanishGreetings implements GreetingsInterface{
/*public void sayGreetings() {
System.out.println(GreetingsInterface.greetings);
}*/
}
À la compilation de la classe SpanishGreetings, nous obtiendrons alors:
SpanishGreetings.java:1: error:
SpanishGreetings is not abstract and does not override abstract method sayGreetings() in GreetingsInterface
public class SpanishGreetings implements GreetingsInterface{
^
1 error
Le message d'erreur nous mentionne que nous n'avons pas redéfinit la méthode abstraite sayGreetings() dans GreetingsInterface. Encore une fois, nous vous rappelons l'importance de bien lire les messages d'erreurs. Ces derniers sont toujours précis sur la nature de votre erreur.
Par ailleurs, une classe peut réaliser (implémenter) plusieurs interfaces en Java.
public interface PartingsInterface{
public void sayPartings();
}
// List the names of the interfaces
// to implement separated by a comma.
public class SchwarzeneggerPhrases implements GreetingInterface, PartingsInterface{
public void sayGreeting() {
System.out.println("I’ll be back");
}
// The class must still implement all the
// methods declared in all the interfaces
public void sayParting() {
System.out.println("Hasta la vista");
}
public static void main(String[] args){
GreetingsInterface myGreetings = new SchwarzeneggerPhrases();
myGreetings.sayGreetings();
PartingsInterface myPartings = new SchwarzeneggerPhrases();
myPartings.sayPartings();
}
}
Il est possible pour une interface d'hériter d'une autre interface tout comme les classes peuvent hériter d'une autre. Vous utiliserez le même mot clé « extends » pour déclarer que votre interface dérive d'une autre. Contrairement aux classes, les interfaces peuvent dériver de multiples « superinterface ». Pour ce faire, vous devez énumérer chacune des interfaces mères en les séparant par des virgules. Voici un exemple simple d'héritage multiple d'une interface:
// TalkingInterface inherits all field and methods
// from GreetingsInterface and PartingsInterface .
public interface TalkingInterface extends GreetingsInterface, PartingsInterface {
public void sayItAll();
}
// A class implementing an interface which inherits
// from multiple interfaces must implement all methods
// from the interface and its superinterfaces
public class HamletTalking implements TalkingInterface {
public void sayGreetings() {
System.out.println("To be or not to be");
}
public void sayPartings() {
System.out.println("That is the question");
}
public void sayItAll() {
sayGreetings();
sayPartings();
}
// We create an instance of HamletTalking in main method
public static void main(String[] args){
TalkingInterface myTalking = new HamletTalking();
myTalking.sayItAll();
}
}
Question 2.3 :
Qu'est-ce qui sera imprimé à la console lors de l'exécution de HamletTalking?
RéponseEn bref:
- Une interface ne contient que des méthodes abstraites. Une méthode est abstraite si elle ne possède pas d'implémentation.
- Le mot clé implements est utilisé pour signifier qu'une classe réalise une interface donnée.
- Lorsqu'une classe réalise une interface, il s'agit en quelque sorte d'un contrat à l'effet que la classe devra implémenter chacune des méthodes de l'interface.
- Vous ne pouvez pas créer une instance d'une interface. Vous devez créer créer une instance de la classe qui implémente cette interface et référencer cette instance à une variable référence dont le type est le nom de l'interface.
- Une classe peut réaliser (« implements ») plusieurs interfaces
- Une interface peut étendre (« extends ») plusieurs interfaces
3 - Les « super » classes
Le mot clé « super » est utilisé pour appeler le constructeur, les méthodes et les propriétés de la classe parent. Si votre méthode remplace (« override ») l'une des méthodes de sa super classe, vous pouvez quand même appeler la méthode remplacée, et ce, en utilisant le mot-clé « super ». Voici des exemples de l'utilisation du mot clé :
- super () appelle le constructeur de la classe parent sans arguments
- super (argument1) est un appel au constructeur de la classe parent qui accepte 1 paramètre du type de « argument1 » (notez que ce constructeur doit exister).
- super peut être utilisé pour appeler les méthodes de la classe parent à savoir super.aMethod ()
- super peut être utilisé pour utiliser les variables de la classe parent à savoir super.aVariable
Important: si l'on veut faire un appel au contructeur de la méthode parent « super() » doit être appelé comme première instruction du constructeur de la classe enfant.
Regardez l'exemple ci-dessous dans lequel Frog est dérivé (« extends ») de la classe Animal et fait deux types de bruit, « Ribbit » et « Bark ».
public class Animal {
protected final String noise;
protected Animal() {
this.noise = "silent";
}
protected Animal(String noise) {
this.noise = noise;
}
public void makeNoise() {
System.out.println(noise);
}
}
public class Frog extends Animal {
private final String noise;
public Frog() {
// constructor call super() must be the
// first statement in a constructor
super("Ribbit"); // call parent constructor
super.makeNoise(); // call parent method
this.noise = "Bark";
// call parent variable and compare to class variable
if (!super.noise.equals(this.noise)) {
makeNoise(); // call class method
}
}
public void makeNoise() {
System.out.println(noise);
}
}
Question 3 :
Si vous créez un nouvel objet de la classe Frog, qu'est-ce qui sera imprimé sur la console?
Réponse