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 :

Constante locale et dépassement capacité du tas


Sujet :

Java

  1. #1
    Membre à l'essai
    Profil pro
    Inscrit en
    Décembre 2008
    Messages
    13
    Détails du profil
    Informations personnelles :
    Localisation : France

    Informations forums :
    Inscription : Décembre 2008
    Messages : 13
    Points : 18
    Points
    18
    Par défaut Constante locale et dépassement capacité du tas
    Bonjour,

    J'ai pour habitude d'utiliser le mot-clé "final" au sein des blocs fonctionnels pour empêcher la réinitialisation de certaines variables locales. Mais j'ai quelques soucis.
    Voici l'exemple qui me pose problème:

    Code : Sélectionner tout - Visualiser dans une fenêtre à part
    1
    2
    3
    4
    5
    6
    7
    void foo(){
      for (String filePath : pathList)
      {
        final MediaTags mediaInfo = new MediaTags (filePath);
        System.out.println ("title: " + mediaInfo.getTitle());
      }
    }
    Cet exemple je l'utilise dans une boucle pour obtenir tout un tas d'informations sur un ensemble de fichiers.
    Au bout d'un moment j'ai une exception de type dépassement de la capacité du tas (heap space) même si je l'augmente en passant un argument à la machine virtuelle.
    Le mot-clé "final" semble donc déclarer les variables locales sur le tas et non sur la pile, puisque quand j'enlève le mot-clé, je n'ai plus d'erreur.
    Sans ce mot-clé, la variable est visiblement sur la pile, elle est supprimée de la mémoire en sortant de la fonction donc tout va bien.

    Mais du coup je n'ai plus cette sécurité qui me garantit que mon bloc de code ne va pas réinitialiser ma variable (qui n'est plus une constante).

    Alors ma question est la suivante: il y a t-il un moyen de déclarer une constante locale à une fonction et qu'elle soit mise sur la pile et non sur le tas ? A ma connaissance il n'existe pas d'autre mot-clé.

    Je vous remercie.

  2. #2
    Membre expert

    Homme Profil pro
    Consultant informatique
    Inscrit en
    Janvier 2004
    Messages
    2 301
    Détails du profil
    Informations personnelles :
    Sexe : Homme
    Localisation : Suisse

    Informations professionnelles :
    Activité : Consultant informatique
    Secteur : Finance

    Informations forums :
    Inscription : Janvier 2004
    Messages : 2 301
    Points : 3 675
    Points
    3 675
    Par défaut
    Citation Envoyé par Catheral29 Voir le message
    il y a t-il un moyen de déclarer une constante locale à une fonction et qu'elle soit mise sur la pile et non sur le tas ?
    Non.

    Mais je pense que c'est un faux problème. Toute variable locale, qu'elle soit final ou pas, est éligible pour le garbage collector, dès la sortie du bloc, si aucune autre référence ne pointe dessus.

    Je doute fort que le problème puisse survenir avec l'extrait indiqué. Une OutOfMemory ne se produit que lorsque le garbage collector, malgré ses tentatives, n'arrive pas à libérer assez de mémoire.

    Peut-on voir le code réel? A tous les coups, les références sont passées et stockées ailleurs...

    PS: malgré tout, ce genre de problèmes peut survenir, dans le cas d'une utilisation incorrecte ou trop dépendante de la méthode "finalize"
    "Le plug gros problème des citations trouvées sur internet, c'est qu'on ne peut jamais garantir leur authenticité"

    Confucius, 448 av. J-C

  3. #3
    Modérateur

    Profil pro
    Inscrit en
    Septembre 2004
    Messages
    12 551
    Détails du profil
    Informations personnelles :
    Localisation : France

    Informations forums :
    Inscription : Septembre 2004
    Messages : 12 551
    Points : 21 607
    Points
    21 607
    Par défaut
    Le mot-clé "final" semble donc déclarer les variables locales sur le tas et non sur la pile, puisque quand j'enlève le mot-clé, je n'ai plus d'erreur.
    Voilà une observation bien étonnante.

    Faisons une expérience : exactement le même code, mais sans le mot-clé final. Tu nous dis que tu obtiens des résultats différents. Mais cela m'étonnerait fort, car le binaire produit (le fichier *.class) est exactement le même dans les deux cas. En effet le mot-clé final ne décrit pas un comportement* pour le programme, c'est une aide au développeur pour lui éviter d'assigner plus d'une fois une variable qui ne devrait pas l'être. Le compilateur n'en tiendra pas compte pour la génération du code binaire.
    * Du moins dans le cas montré ici : variable locale et qui n'est pas mise à portée d'une classe locale. Pour une variable locale accédée par une classe locale, il y a bel et bien un comportement ajouté. Et pour une variable membre, le fait qu'elle ne puisse pas être réassignée est une information utile à la JVM, qui pourra décider d'adapter son comportement.

    Autrement dit, dans l'exemple que tu nous proposes, ce dont tu nous parles n'existe pas. Ou alors tu as employé un compilateur bizarre qui a produit des résultats différents sans raison.
    Sans doute observes-tu une différence, dans des situations plus complexe. Et du coup, cette différence n'a peut-être rien à voir avec le mot-clé final, et plutôt avec ce que tu ne nous as pas montré.

    Concernant ta question :
    En principe on n'indique pas à Java s'il doit allouer sur la pile ou dans le tas : la JVM fera le plus efficace qu'elle sait faire. En l'occurrence et si ma mémoire est bonne, dans ce code, si ta classe MediaTags est immutable et que la JVM sait le détecter (Ce serait surprenant vu qu'il y a sans doute ouverture et analyse de fichier,) elle devrait logiquement stocker l'objet sur la pile le temps de s'en servir. Sinon, dans le tas. Le mot-clé final n'ayant aucune incidence dessus, puisqu'il a disparu après compilation.
    N'oubliez pas de consulter les FAQ Java et les cours et tutoriels Java

  4. #4
    Membre à l'essai
    Profil pro
    Inscrit en
    Décembre 2008
    Messages
    13
    Détails du profil
    Informations personnelles :
    Localisation : France

    Informations forums :
    Inscription : Décembre 2008
    Messages : 13
    Points : 18
    Points
    18
    Par défaut
    Oui effectivement c'est curieux, je n'ai jamais eu ce genre de problème.
    Non l'objet crée n'est référencé nul part ailleurs.

    Vous avez certainement raison, c'est peut-être un scénario d'exécution particulier qui a provoqué l'erreur.
    Je ne dispose pas du code source de l'objet crée, j'ai trouvé une autre lib alternative et ça semble fonctionner.

    En tout cas merci pour votre aide. Si ça vient de la lib, j'ignore quel est le problème, en tout cas maintenant ça semble marcher de nouveau !

  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,


    Il faudrait connaitre l'erreur exact (le stacktrace) et la bibliothèque en question pour comprendre l’origine de tout cela.



    Sinon je confirme le mot-clef final sur une variable locale n'a aucune incidence sur le bytecode généré ou les optimisations de la JVM.

    Sauf dans un cas bien précis : lorsque qu'il correspond à une constante au sens Java (variable primitif ou String déclaré en ligne et évaluable à la compilation).
    Dans ce cas le compilateur supprimera carrément la variable et la remplacement par sa valeur...


    a++

  6. #6
    Membre expert

    Homme Profil pro
    Consultant informatique
    Inscrit en
    Janvier 2004
    Messages
    2 301
    Détails du profil
    Informations personnelles :
    Sexe : Homme
    Localisation : Suisse

    Informations professionnelles :
    Activité : Consultant informatique
    Secteur : Finance

    Informations forums :
    Inscription : Janvier 2004
    Messages : 2 301
    Points : 3 675
    Points
    3 675
    Par défaut
    Citation Envoyé par Catheral29 Voir le message
    Non l'objet crée n'est référencé nul part ailleurs.
    ça ne veut pas dire que la lib ne stocke pas les références des objets créés quelque part

    ex: mise en cache d'instances dans une collection statique interne, mal implémenté, etc.

    si on connaissait la lib, on pourrait certainement en dire plus...
    "Le plug gros problème des citations trouvées sur internet, c'est qu'on ne peut jamais garantir leur authenticité"

    Confucius, 448 av. J-C

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

Discussions similaires

  1. dépassement capacité winXP
    Par lautrec1 dans le forum C
    Réponses: 4
    Dernier message: 09/11/2014, 13h57
  2. Checksum - Pb dépassement capacité variable
    Par dede38440 dans le forum VB.NET
    Réponses: 0
    Dernier message: 22/08/2014, 13h43
  3. [XL-2007] VBA : dépassement capacité calcul moyenne
    Par BaelBender dans le forum Macros et VBA Excel
    Réponses: 2
    Dernier message: 10/06/2014, 15h28
  4. [XL-2010] DEB Boucle dépassement capacité
    Par torquemada dans le forum Macros et VBA Excel
    Réponses: 2
    Dernier message: 22/04/2013, 18h12
  5. détection de dépassement de capacité
    Par tut dans le forum C++
    Réponses: 10
    Dernier message: 01/12/2004, 22h11

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