Bonjour. Bienvenue dans cette quatrième séquence sur l'héritage
et le lookup.
Dans cette séquence nous allons voir ce qui se passe
quand l'algorithme de lookup ne trouve pas une méthode
correspondante à un message.
Alors on va voir que le code, les classes, sont capables
d'ajouter du traitement pour traiter le fait qu'
un message aurait été envoyé et qui n'aurait pas été compris.
Si je reviens rapidement sur l'envoi de messages.
On envoie le message area à l'objet colored rectangle.
L'algorithme de lookup a pour but de trouver la méthode à
exécuter par rapport à ce message là, donc l'algorithme
de lookup cherche dans la classe du receveur, c'est-à-dire
ColoredRectangle, une méthode qui s'appelle area, s'il la
trouve, il l'exécute.
Là il ne la trouve pas donc l'algorithme de lookup va
aller voir dans la superclasse. La méthode area est
trouvée et elle est exécutée sur le receveur.
Alors qu'est-ce-qui se passe s'il n'y a pas de méthode
area du tout, et que algorithme de lookup échoue?
Alors dans ce cas-là on envoie le message "Coucou" à l'objet node1.
Il n'y a pas de méthode Coucou implémentée, donc l'envoi
de message se passe comment ?
On envoie le message Coucou à node1, on cherche Coucou
dans la classe Node il n'est pas trouvé, l'algorithme de
lookup cherche Coucou dans la classe Object, il n'est pas trouvé.
À ce moment-là, la machine virtuelle Pharo envoie le
message doesNotUnderstand au receveur donc
à node1. Donc doesNotUnderstand
avec le message initial en paramètres, donc avec
un coucou: stef en paramètre.
Ici, si je le refais étape par étape, coucou est envoyé à
node1, Coucou est cherché dans la classe Node, Coucou est
cherché dans la classe Object, la méthode Coucou n'existe
pas donc le message doesNotUnderstand est envoyé à l'objet node1.
Donc l'algorithme de lookup va chercher une méthode
doesNotUnderstand dans la classe de node1.
DoesNotUnderstand n'est pas trouvé dans la classe Node
donc l'algorithme de lookup charge doesNotUnderstand dans
la super classe, la méthode doesNotUnderstand est trouvée
ou une méthode doesNotUnderstand est trouvée dans la
classe Object, elle est exécutée.
Donc qu'est ce que ça signifie ça ?
Ça signifie que dans toutes les sous-classes de la classe
Object, on peut implémenter doesNotUnderstand pour avoir
du comportement particulier qui va s'exécuter lorsqu'un
objet, une instance de cette classe ne comprend pas un message.
Donc sur ce slide vous avez les détails étape par étape
de cet exemple que vous pouvez relire.
DoesNotUnderstand, c'est un message comme les autres.
Donc vous pouvez implémenter une méthode qui s'appelle
doesNotUnderstand, et qui sera exécutée à chaque fois qu'une
instance ne comprendra pas un message.
On se sert de ce mécanisme dans certains cas un petit peu
compliqués comme les proxys, la délégation
automatique, c'est-à-dire lorsque vous voulez que tous
les messages que reçoit un objet soient transmis à un autre objet.
Dans ces cas-là on peut utiliser ce mécanisme de doesNotUnderstand.
L'implémentation par défaut de doesNotUnderstand se
trouve dans la classe object, et cette implémentation par
défaut lève une exception. Donc l'exception
s'appelle "MessageNotUnderstood".
Donc si la méthode doesNotUnderstand de la classe object
est exécutée, une exception est levée.
Cela signifie que le code que vous écrivez peut capturer
cette exception, comme il capturerait n'importe quelle
exception, et peut y avoir du traitement particulier
lorsqu'un message n'est pas compris.
Dans cet exemple là, on revient sur la classe Node, et
on a une méthode "sayHello" dans la classe Node, qui
envoie le message Coucou au receveur donc à self.
On a aussi une méthode Welcome qui envoie le message
"Sayhello" à self et qui fait un traitement particulier
si dans le contexte de cet envoi de message,
si un message n'est pas compris, il va y avoir du traitement.
Donc là say hello envoie le message Coucou à self, Coucou
n'est toujours pas implémenté, donc au final la méthode
doesNotUnderstand sera exécutée,
une exception sera levée, donc l'exception messageNotUnderstood sera levée.
Le code qui est ici avec undo sert à capturer les
exceptions, c'est l'équivalent de try catch en Java.
Vous aurez une séquence plus tard qui vous parlera des exceptions en détail.
Mais là ce qui nous intéresse c'est de voir que ce
code-là, en fait, c'est l'équivalent du catch de Java,
donc c'est le code qui va être exécuté lorsque l'exception est capturée.
Donc si on envoie le message Welcome à node1,
sachant que Coucou n'est pas implémenté, on affichera
dans la console le message something went wrong with the message.
Ce que vous devez retenir, c'est que
lorsque l'algorithme de lookup ne trouve pas une méthode
correspondante à un message qui est envoyé, un message
doesNotUnderstand est envoyé au receveur initial avec le
message d'origine en paramètres.
Vous pouvez implémenter une méthode doesNotUnderstand dans vos classes.
A défaut, l'implémentation par défaut dans la classe object sera exécutée.
Cette implémentation par défaut lève une exception, cette
exception s'appelle messageNotUnderstood, et le code que
vous écrivez peut capturer cette exception et avoir du
traitement particulier lorsqu'un message n'est pas compris.