Next: Délégation
Up: Héritage et polymorphisme vertical
Previous: Comment traiter de façon
La nécessité du polymorphisme vertical
Finalement, il y a plein de cas où on a besoin de recuperer le pouvoir expressif
du polymorphisme vertical pour éviter une prolifération massive du nombre de
classes dans le programme. Un exemple est encore bien sûr la liste, mais on peut
choisir autre chose, comme la classe Matrix de Objective-C qui fournit une
matrice de cellules affichables. Si on veut vraiment que le typage soit vérifié
statiquement, on est obligé de demander quelque chose du type des cellules, et
si on n'a rien d'autre que l'héritage sous la main, on se retrouve vite avec une
sous-classe de Matrix pour tout type de cellules dans le programme.
Il y a plusieurs façons de répondre à ce problème: on examinera ici les classes paramétriques et le vrai polymorphisme à la ML.
- classes paramétriques
- dans C++, on fournit à l'utilisateur
le mécanisme des classes paramétriques (aussi
appelé genericity ) pour simuler le polymorphisme
vertical, mais il s'agit essentiellement d'un gros hack qui
se résout en une macro-expansion. Il n'y a pas là le
partage de code possible en ML, et on se retrouve à peu près
avec quelque chose de moins que les generic
packages de ADA.
Voici un exemple très simple en C++ pour des points à coordonnées entières ou flottantes.#include <fstream.h> //------------------------------ template <class T> class Point {private: T x; public: T getx(); void setx(T x); };
template<class T> T Point<T>::getx() { return x; }
template<class T> void Point<T>::setx(T v) { x=v; }
//------------------------------
main() { Point<int> p; Point<float> q; p.setx(3); q.setx(4.33); cout<<p.getx()<<" "<<q.getx()<<"\n"; exit(0); }
- vrai polymorphisme à la ML
- Comparez le code C++ que l'on a été obligé d'écrire
ci-dessus avec le fragment Objective Caml suivant, qui exploite le vrai polymorphisme vertical:
#class 'a point x =
val mutable x = x
method setx (y:'a) = x <-y
end;;
class 'a point ('a) = val x : 'a method setx : 'a -> unit end
new point 3;;
- : int point = <obj>
new point 4.33;;
- : float point = <obj>
- : int point = <obj>
Roberto DiCosmo
Mon Jun 3 18:29:31 MET DST 1996