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

Langage Java Discussion :

"String" constantes ou pas?


Sujet :

Langage Java

  1. #1
    Membre expert
    Avatar de Pragmateek
    Homme Profil pro
    Formateur expert .Net/C#
    Inscrit en
    Mars 2006
    Messages
    2 635
    Détails du profil
    Informations personnelles :
    Sexe : Homme
    Âge : 38
    Localisation : France, Val de Marne (Île de France)

    Informations professionnelles :
    Activité : Formateur expert .Net/C#
    Secteur : Conseil

    Informations forums :
    Inscription : Mars 2006
    Messages : 2 635
    Points : 3 958
    Points
    3 958
    Par défaut "String" constantes ou pas?
    Salut!

    On peut lire dans la javadoc:
    Strings are constant; their values cannot be changed after they are created.
    Pourtant:
    Code : Sélectionner tout - Visualiser dans une fenêtre à part
    1
    2
    3
    4
    String s1="azerty";
    s1="az";
    s1="azertyuiop";
    s1=s1.replace('a','b');
    est tout à fait valide.

    Que signifie exactement le terme "constant" et "cannot be changed".

    Merci de vos explications.

  2. #2
    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,

    Citation Envoyé par seriousme
    Que signifie exactement le terme "constant" et "cannot be changed".
    Cela signifie qu'une fois qu'un objet String est crée, il ne peut plus être modifié (on parle aussi de classe immuable). Tu n'a pas de méthode setValue() qui modifie l'objet courant, mais uniquement des méthodes qui renvoient un nouvel objet...

    En fait a chaque fois que tu modifies la String dans ton code, tu affectes une nouvelle référence, et donc il s'agit d'un nouvel objet. Tu peux vérifier cela en utilisant la méthode System.identityHashCode() qui te renvoit un identifiant unique par objet :
    Code : Sélectionner tout - Visualiser dans une fenêtre à part
    1
    2
    3
    4
    5
    6
    7
    8
            String s1="azerty";
            System.out.println( "s1 = " + System.identityHashCode(s1) );
            s1="az";
            System.out.println( "s1 = " + System.identityHashCode(s1) );
            s1="azertyuiop";
            System.out.println( "s1 = " + System.identityHashCode(s1) );
            s1=s1.replace('a','b');
            System.out.println( "s1 = " + System.identityHashCode(s1) );
    Tu verras que tu obtiens 4 valeurs différentes...



    Ce principe de classe immuable est très présent en Java et permet de gérer simplement les données. Par exemple lorsque tu récupères un objet immuable en paramètre d'une méthode, tu sais qu'il ne pourra pas être modifié de "l'extérieur" et tu peux donc le conserver tel quel...

    Par exemple la classe Long est immuable, alors que la classe Date ne l'est pas car elle comporte une méthode setTime() qui permet de modifier sa valeur (d'ailleurs plusieurs personnes pensent que Date aurait du être immuable également).
    Ainsi si tu écris la classe suivante :
    Code : Sélectionner tout - Visualiser dans une fenêtre à part
    1
    2
    3
    4
    5
    6
    7
    8
    9
    10
    11
    12
    13
    14
    class Test {
        Long longValue;
        Date dateValue;
     
        public Test(Long l, Date d){
            this.longValue = l;
            this.dateValue = d;
        }
     
        @Override
        public String toString() {
            return "(Long=" + longValue + ", Date=" + dateValue.getTime() + ")";
        }
    }
    Tu sais que son attribut longValue ne pourra pas être modifié après la création de l'objet. Par contre rien n'est sûr en ce qui concerne l'attribut dateValue...

    Le code suivant le montre très bien :
    Code : Sélectionner tout - Visualiser dans une fenêtre à part
    1
    2
    3
    4
    5
    6
    7
    8
    9
    10
            Long l1 = new Long(100);
            Date d1 = new Date(100);
            Test t = new Test(l1, d1);
            
            System.out.println(t); // Affiche (Long=100, Date=100)
            
            l1 = new Long(200); // Cree un nouvel objet Long
            d1.setTime(200);    // Modifie l'objet courant et celui de l'objet 'Test'
            
            System.out.println(t); // Affiche (Long=100, Date=200)
    La valeur du champs dateValue est modifié de l'extérieur de la classe, ce qui peut poser problème dans certain cas...

    Du coup tu es obligé de créer un nouvel objet Date si tu veux pouvoir le protéger des modifications depuis l'extérieur :
    Code : Sélectionner tout - Visualiser dans une fenêtre à part
    1
    2
    3
    4
        public Test(Long l, Date d){
            this.longValue = l;
            this.dateValue = new Date(d.getTime());
        }
    a++

  3. #3
    Membre expert
    Avatar de Pragmateek
    Homme Profil pro
    Formateur expert .Net/C#
    Inscrit en
    Mars 2006
    Messages
    2 635
    Détails du profil
    Informations personnelles :
    Sexe : Homme
    Âge : 38
    Localisation : France, Val de Marne (Île de France)

    Informations professionnelles :
    Activité : Formateur expert .Net/C#
    Secteur : Conseil

    Informations forums :
    Inscription : Mars 2006
    Messages : 2 635
    Points : 3 958
    Points
    3 958
    Par défaut
    OK merci.
    Le GC est il invoqué à chaque nouvelle affectation pour détruire "l'ancienne" "s1" et y a t'il création d'un nouvel objet "String" à chaque fois ou est-ce plus subtil?

  4. #4
    Expert éminent sénior
    Avatar de Baptiste Wicht
    Homme Profil pro
    Étudiant
    Inscrit en
    Octobre 2005
    Messages
    7 431
    Détails du profil
    Informations personnelles :
    Sexe : Homme
    Âge : 36
    Localisation : Suisse

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

    Informations forums :
    Inscription : Octobre 2005
    Messages : 7 431
    Points : 21 324
    Points
    21 324
    Par défaut
    Citation Envoyé par seriousme
    OK merci.
    Le GC est il invoqué à chaque nouvelle affectation pour détruire "l'ancienne" "s1" et y a t'il création d'un nouvel objet "String" à chaque fois ou est-ce plus subtil?
    Je crois pas que ce soit beaucoup plus subtil.

    Lors d'une opération comme celle-ci :

    Code : Sélectionner tout - Visualiser dans une fenêtre à part
    1
    2
    String chaine1 = "Chaine 1";
    chaine1 = "Chaine 2";
    Ca va faire quelque chose comme ca :

    • Création d'un nouvel objet pointant sur Chaine 1
    • On fait pointer chaine1 sur Chaine 2
    • Il n'y a donc plus aucune référence pointant sur Chaine 1, il devient donc candidat au ramasse-miettes
    • Ca fait donc un objet qui sert à rien qui prend de la mémoire tant que le ramasse-miettes n'est pas passé

  5. #5
    Expert éminent sénior


    Profil pro
    Inscrit en
    Octobre 2003
    Messages
    7 856
    Détails du profil
    Informations personnelles :
    Localisation : France

    Informations forums :
    Inscription : Octobre 2003
    Messages : 7 856
    Points : 34 380
    Points
    34 380
    Par défaut
    Pour information, dans le cas d'une concaténation :

    Code : Sélectionner tout - Visualiser dans une fenêtre à part
    1
    2
    3
    public String getString(String str1,String str2) {
                return str1+str2;
    }
    se transforme après compilation en :

    Code : Sélectionner tout - Visualiser dans une fenêtre à part
    1
    2
    3
    public String getString(String str1,String str2) {
               return new StringBuffer().append(str1).append(str2).toString();
    }

  6. #6
    Membre expert
    Avatar de Pragmateek
    Homme Profil pro
    Formateur expert .Net/C#
    Inscrit en
    Mars 2006
    Messages
    2 635
    Détails du profil
    Informations personnelles :
    Sexe : Homme
    Âge : 38
    Localisation : France, Val de Marne (Île de France)

    Informations professionnelles :
    Activité : Formateur expert .Net/C#
    Secteur : Conseil

    Informations forums :
    Inscription : Mars 2006
    Messages : 2 635
    Points : 3 958
    Points
    3 958
    Par défaut
    Merci à tous de vos réponses.

+ Répondre à la discussion
Cette discussion est résolue.

Discussions similaires

  1. Fonction Quoted printable qui ne fonctionne pas.
    Par leCcsympas dans le forum C
    Réponses: 3
    Dernier message: 13/01/2007, 18h54

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