Programmation pour le TAL

Membres et méthodes statiques : application

On peut attribuer un nom à tout objet géométrique via la méthode setObjName(). Pour les objets auxquels on n'a pas affecté de nom, la valeur par défaut est "anonymous". On souhaite que tous les "objets anonymes" aient un nom différent. Pour cela, on souhaiterait compter tous les objets géométriques qui ont été créés au cours de l'exécution du programme et appeler chaque objet "anonymous1", "anonymous2", etc., tant qu'on ne leur a pas attribué de nom.

Comptage des objets

On a vu dans le cours sur les membres et méthodes statiques qu'on pouvait doter la class GeomObject d'un membre statique nbCreatedObjects, de type int, initialisé à 0. On peut également ajouter dans GeomObject une méthode statique incNbCreatedObjects() qui incrémente nbCreatedObjects. Mais où (qui) doit invoquer cette méthode et quand ? La réponse à la dernière question (quand ?) est "chaque fois que l'on crée un nouvel objet". Mais comment ? Ce n'est pas à l'utilisateur des différentes classes MobilePoint, Triangle, Circle, etc. dérivées de GeomObject de le faire. Si vous n'en êtes pas convaincu, revoyez notamment le transparent 13 de la présentation "Programmation orientée objets : notions" de la séance 2. On peut envisager d'invoquer incNbCreatedObjects() dans les constructeurs des classes dérivées. Mais il faut ajouter cette instruction dans tous les constructeurs sans en oublier ! Et il ne faudra pas en oublier à l'avenir si on crée d'autres classes dérivées. Mais... dans tous les constructeurs, vraiment ?
    public class Segment extends GeomObject
    {
	private MobilePoint endPoint1 = null;
	private MobilePoint endPoint2 = null;
	
	public Segment (MobilePoint endPoint1, MobilePoint endPoint2)
	{
	    this.endPoint1 = endPoint1;
            this.endPoint2 = endPoint2;
            incNbObject ();
	} // public Segment ()
	
	public Segment (MobilePoint endPoint1, MobilePoint endPoint2, String objName)
	{
	    this (endPoint1, endPoint2);
	    setObjName(objName);
	    // Attention : pas de incNbObject car on invoque le constructeur défini plus haut
	    // (dans lequel est déjà invoqué incNbObject ())
	} // public Segment ()

       // ...
    }
    

Autre solution : ne pas invoquer incNbCreatedObjects() dans les classes dérivées, mais effectuer l'incrémentation dans le(s) constructeur(s) de la classe GeomObject elle-même. S'il y avait plusieurs constructeurs dans GeomObject, il faudrait penser à incrémenter la variable dans chacun des constructeurs (sauf ceux qui invoquent this()). En l'occurrence, il n'y avait pas encore de constructeur dans la classe (à l'exception du constructeur par défaut). Il suffit donc de redéfinir le constructeur par défaut qui sera appelé, explicitement ou implicitement, à chaque création d'objet géométrique (i.e. d'une instance d'une classe dérivée). L'invocation est explicite si, dans le constructeur d'une classe qui dérive directement de GeomObject, on invoque super(). S'il n'y a pas d'invocation de cette méthode dans le constructeur d'une classe qui dérive directement de GeomObject, l'appel au constructeur par défaut de GeomObject se fait quand-même : il est implicite. Pour vous en convaincre, ajoutez une trace d'exécution : System.out.println ("Passage dans constructeur de GeomObject"); dans la classe GeomObject.

    public class GeomObject
    {
	private static int nbCreatedObjects = 0;
	
	public GeomObject ()
	{
		nbCreatedObjects++;
		System.out.println("Passage dans constructuer de GeomObject");
	} // GeomObject ()
    }
      

Nommage

Une fois que le mécanisme de comptage des objets est en place, il suffit d'attribuer à l'objet (en attendant un éventuel appel ultérieur à setObjName()) un nom qui comporte le numéro d'objet. On réalise ce nommage une fois, en même temps que l'incrémentation du compteur statique :

    public class GeomObject
    {
	private static int nbCreatedObjects = 0;
	private String objName = null;
	
	public GeomObject ()
	{
		nbCreatedObjects++;
		setObjName("anonymous_" + String.valueOf(nbCreatedObjects));
	} // GeomObject ()
    }


Retour page séance 7 ]

Mention légale ]