IdentifiantMot de passe
Loading...
Mot de passe oublié ?Je m'inscris ! (gratuit)
Navigation

Inscrivez-vous gratuitement
pour pouvoir participer, suivre les réponses en temps réel, voter pour les messages, poser vos propres questions et recevoir la newsletter

Java Discussion :

Techniques de clonage


Sujet :

Java

  1. #1
    Membre actif

    Inscrit en
    Mai 2002
    Messages
    328
    Détails du profil
    Informations personnelles :
    Âge : 44

    Informations forums :
    Inscription : Mai 2002
    Messages : 328
    Points : 209
    Points
    209
    Par défaut Techniques de clonage
    Hello,

    Comment implémentez-vous le clonage profond de vos objets ? Pourquoi ?

    Globalement j'ai deux choix : surcharger la méthode clone() de mes objets ou bien écrire une méthode de copie générale externe s'occupant de tous les objets...

    Merci !

    Toine

  2. #2
    Modérateur
    Avatar de dinobogan
    Homme Profil pro
    ingénieur
    Inscrit en
    Juin 2007
    Messages
    4 073
    Détails du profil
    Informations personnelles :
    Sexe : Homme
    Âge : 42
    Localisation : France

    Informations professionnelles :
    Activité : ingénieur
    Secteur : High Tech - Éditeur de logiciels

    Informations forums :
    Inscription : Juin 2007
    Messages : 4 073
    Points : 7 163
    Points
    7 163
    Par défaut
    La méthode de copie générale doit connaitre tous les objets, et faire de l'introspection pour les données internes privées sans accesseurs, et c'est lent. En plus, lors de la création d'un nouvel objet, il faut aussi modifier le super objet de copie générale.
    C'est pour ces raisons que l'objet lui-même doit se débrouiller pour se cloner. Il sait comment il fonctionne, il a accès à toutes les données directement.
    N'oubliez pas de consulter les FAQ Java et les cours et tutoriels Java
    Que la force de la puissance soit avec le courage de ta sagesse.

  3. #3
    Membre actif

    Inscrit en
    Mai 2002
    Messages
    328
    Détails du profil
    Informations personnelles :
    Âge : 44

    Informations forums :
    Inscription : Mai 2002
    Messages : 328
    Points : 209
    Points
    209
    Par défaut
    Ok, je suis aussi partisan de cette technique.

    Maintenant, il parait qu'il ne faut pas employer de constructeur dans la méthode clone, avez en "pattern", des règles pour écrire cette méthode ?

  4. #4
    Membre expert
    Avatar de natha
    Profil pro
    Inscrit en
    Janvier 2006
    Messages
    2 346
    Détails du profil
    Informations personnelles :
    Localisation : Suisse

    Informations forums :
    Inscription : Janvier 2006
    Messages : 2 346
    Points : 3 083
    Points
    3 083
    Par défaut
    Clone ça marche très bien.
    Il ne faut effectivement pas appeler de constructeur à cause de l'héritage, c'est pour ça qu'il faut toujours appeler super.clone() si vous surcharger clone.
    Comment ça ? La réponse à ton problème n'est ni dans la faq, ni dans les tutos, ni dans sources ??? Etonnant...
    De la bonne manière de poser une question (et de répondre).
    Je ne fais pas de service par MP. Merci (...de lire les règles...).
    Ma page dvp.com

  5. #5
    Expert éminent sénior
    Avatar de adiGuba
    Homme Profil pro
    Développeur Java/Web
    Inscrit en
    Avril 2002
    Messages
    13 938
    Détails du profil
    Informations personnelles :
    Sexe : Homme
    Localisation : France

    Informations professionnelles :
    Activité : Développeur Java/Web
    Secteur : Transports

    Informations forums :
    Inscription : Avril 2002
    Messages : 13 938
    Points : 23 190
    Points
    23 190
    Billets dans le blog
    1
    Par défaut
    Salut,



    Grosso-modo j'utilise cette forme là :
    Code : Sélectionner tout - Visualiser dans une fenêtre à part
    1
    2
    3
    4
    5
    6
    7
    8
    9
    10
    11
    12
    13
    14
    15
    16
    17
    18
    19
    20
    21
    22
    23
    24
    25
    26
    class MonObject implements Cloneable {
     
    	private String name;
    	private Date date;
     
    	public MonObject(String name) {
    		this.name = name;
    		this.date = new Date();
    	}
     
    	public Object clone() {
    		try {
    			// On clone l'objet courant :
    			MonObject clone = (MonObject)super.clone();
     
    			// On clone les eventuels attributs a protéger
    			clone.date = (Date)clone.date.clone();
     
    			// Et on retourne la valeur obtenu :
    			return clone;
    		} catch (CloneNotSupportedException e) {
    			// Cela ne devrait jamais arriver :
    			throw new RuntimeException(e);
    		}
    	}
    }
    • On passe clone() en public pour faciliter son utilisation (mais cela dépend aussi du besoin).
    • On commence par appeler super.clone(), qui doit retourner le type réel de l'instance (donc éventuellement une classe fille).
    • On duplique aussi les éventuels attributs a protéger via encapsulation. C'est inutile pour les types immuables (comme String).
    • Enfin perso je reduis l'exception au silence, puisqu'elle ne devrait jamais arriver. Cela permet une utilisation plus simple du clone() (il n'y a pas d'obligation à gérer les RuntimeExceptions).




    A noter qu'avec Java 5.0 on peut utiliser la covariance du type de retour, afin d'éviter de se trainer des Object et des cast :
    Code : Sélectionner tout - Visualiser dans une fenêtre à part
    1
    2
    3
    4
    5
    6
    7
    8
    9
    10
    11
    12
    13
    14
    15
    16
    	@Override
    	public MonObject clone() {
    		try {
    			// On clone l'objet courant :
    			MonObject clone = (MonObject)super.clone();
     
    			// On clone les eventuels attributs a protéger
    			clone.date = (Date)clone.date.clone();
     
    			// Et on retourne la valeur obtenu :
    			return clone;
    		} catch (CloneNotSupportedException e) {
    			// Cela ne devrait jamais arriver :
    			throw new RuntimeException(e);
    		}
    	}

    a++

  6. #6
    Membre actif

    Inscrit en
    Mai 2002
    Messages
    328
    Détails du profil
    Informations personnelles :
    Âge : 44

    Informations forums :
    Inscription : Mai 2002
    Messages : 328
    Points : 209
    Points
    209
    Par défaut
    Merci pour les réponses détaillées

    CloneNotSupportedException peut se produire dans mon cas car je permet l'ajout de module externe...

    Sinon, je suis parti sur la définition d'une interface propre Cloneable étendant la Cloneable du JDK

    Maintenant, avez-vous eu des soucis d'implémentation du clonage ? Je pense en particulier au "deep clone"...

    Anthony

  7. #7
    Nouveau membre du Club
    Inscrit en
    Juillet 2007
    Messages
    42
    Détails du profil
    Informations forums :
    Inscription : Juillet 2007
    Messages : 42
    Points : 38
    Points
    38
    Par défaut
    J'ai recemment utiliser un clone Hybride
    du type
    Dans un exemple Area contient des attributs dont un qui est du Tyoe Properties
    Code : Sélectionner tout - Visualiser dans une fenêtre à part
    1
    2
    3
    4
    5
    6
    7
    8
    9
    10
    11
     
    public Object clone(String baseName, Template template) {
    		Area res = null;
    		try {
    			res = (Area) super.clone();
    		} catch (CloneNotSupportedException e) {
    		}
    		res.setId(id + "/" + baseName);
    		res.setProperties((Properties) properties.clone(baseName, template));
    		return res;
    	}
    En gros j'écris ma propre méthode clone (qui ne surchage pas clone de Object puisqu'avec un paramètre) mais j'appelle bien la méthode super.clone().
    Pour le deep clone, effectivement il faut le faire à la main (dans mon cas écrire le clone(String aaa) dans Properties).
    Enfin je ne fait pas remonter l'exception pour ne pas avoir a gérer des cas impossible.

  8. #8
    Membre actif

    Inscrit en
    Mai 2002
    Messages
    328
    Détails du profil
    Informations personnelles :
    Âge : 44

    Informations forums :
    Inscription : Mai 2002
    Messages : 328
    Points : 209
    Points
    209
    Par défaut
    Intéressant, le template te sert à quoi dans ton cas ? Une sorte de contexte ?

    Pour le "deep clone", je le fais aussi à la main... Il y a bien la possibilité de le faire par sérialisation d'une grappe d'objets ou alors via une méthode supra-intelligente basée sur la réflexion, mais finalement ces techniques restent consommatrices et lentes...

    Anthony

Discussions similaires

  1. LES TECHNIQUES DES SGBDR / MySQL rapide ???
    Par SQLpro dans le forum Langage SQL
    Réponses: 1
    Dernier message: 12/09/2003, 11h16
  2. [Compilateurs] Sites techniques
    Par Traroth dans le forum Langages de programmation
    Réponses: 4
    Dernier message: 26/03/2003, 09h11
  3. [Technique] Conflits entre plusieurs requêtes
    Par Neowile dans le forum Décisions SGBD
    Réponses: 3
    Dernier message: 24/03/2003, 09h37
  4. [Technique] Intérêt des index
    Par ddams dans le forum Décisions SGBD
    Réponses: 10
    Dernier message: 04/11/2002, 15h11
  5. [Technique] Index, comment font les moteurs de recherche ?
    Par bat dans le forum Décisions SGBD
    Réponses: 4
    Dernier message: 25/10/2002, 15h41

Partager

Partager
  • Envoyer la discussion sur Viadeo
  • Envoyer la discussion sur Twitter
  • Envoyer la discussion sur Google
  • Envoyer la discussion sur Facebook
  • Envoyer la discussion sur Digg
  • Envoyer la discussion sur Delicious
  • Envoyer la discussion sur MySpace
  • Envoyer la discussion sur Yahoo