OVH Cloud OVH Cloud

OutOfMemoryError avec des images

6 réponses
Avatar
oliv
Bonjour,

j'ai un petit bout de programme qui consiste en une classe View
héritant de Jframe qui doit permettre de traiter et visualiser
successivement les images d'un directory.

Après "un certain" nombre d'images ~20 j'ai une OutOfMemoryError.

Le schéma de l'allocation est :

main() :
for (int i=0 ; i<fnames.length ; i++) {
try {
view = new View(new URL("file://" + root + "/" + fnames[i]));
view.process(3, 3, 1);
view.setVisible(true);
try { Thread.sleep(2000);} catch (InterruptedException ex) {};
view.setVisible(false);
view = null;
}
catch (java.net.MalformedURLException ex) { ex.printStackTrace();}
}

Les images sont chargées par View.image =
Toolkit.getDefaultToolkit().getImage(url);
avec un mediaTracker.

J'ai compté qu'en mettant à null la référence view, le GC gererait le
dispose de la view et donc de la variable d'instance image.

Qu'est-ce que j'ai raté ?

Faudrait-il (peut-on ?) libérer explicitement View.image ?

Faudrait-il appeler explictement le GC ?

Merci pour votre aide.

--
Olivier
This space for sale.

6 réponses

Avatar
Libert Sébastien
"oliv" a écrit dans le message de news:
bnuj4e$b1p$

Après "un certain" nombre d'images ~20 j'ai une OutOfMemoryError.

Faudrait-il (peut-on ?) libérer explicitement View.image ?

Faudrait-il appeler explictement le GC ?


Salut !

Sorry, je n'ai pas de réponse directe. A ta place, j'utiliserais un
profiler, histoire de suivre un peu de déroulement des histoires et de voir
ce qui n'est pas libéré.

Une liste de profilers : http://pharos.inria.fr/Java/query.jsp?text=profiler



HTH
Sébastien Libert.

Avatar
oliv
Libert Sébastien wrote:
Sorry, je n'ai pas de réponse directe. A ta place, j'utiliserais un
profiler, histoire de suivre un peu de déroulement des histoires et de voir
ce qui n'est pas libéré.

Une liste de profilers : http://pharos.inria.fr/Java/query.jsp?text=profiler

Merci pour ta réponse, je vais en effet aller voir.


Entretemps, d'après ce que j'ai pu trouver ici et là, j'ai essayé de
rajouter a View :

public void dispose() {
image.flush();
image = null;
System.gc();
}

et de l'appeler avant chaque changement d'image, mais ça ne change rien.

--
Olivier
This space for sale.

Avatar
batyann811
view = new View(new URL("file://" + root + "/" + fnames[i]));


Je vais peut-être dire une connerie mais si ta classe View hérite de
JFrame je crois qu'à chaque fois que tu fais un new JFrame tu creés
effectivement une nouvelle fenêtre sans détruire le précédente car la
fenêtre est crée dans un autre thread que ton main() et donc même quand
tu fais view=null elle n'est pas libérée car encore référencée dans
l'autre thread. Il faut peut-être que tu provoque la destruction de la
fenêtre par un view.dispose() je crois.

Mais bon comme je l'ai déjà dit c'est peut-être une connerie car ça fait
peu de temps que j'utilise java.

--
batyann811


Avatar
Libert Sébastien
Salut !

Tu trouveras sur http://mindprod.com/jgloss/dispose.html un petit résumé des
bonnes habitudes pour bien libérer des (J)Frame.
En gros, il conseille surtout de redéfinir dispose et de bien penser à tout
libérer (listeners, etc.)
De nouveau, pour ne rien oublier... hop un bon profiler ;-)



HTH
Sébastien Libert.
Avatar
oliv
batyann811 wrote:
Je vais peut-être dire une connerie mais si ta classe View hérite de
JFrame je crois qu'à chaque fois que tu fais un new JFrame tu creés
effectivement une nouvelle fenêtre sans détruire le précédente
Non, c'est bien comme ça que je vois les choses et c'était voulu, mais

il faudra peut-être plutôt changer ce "design" car ...

Il faut peut-être que tu provoque la destruction de la
fenêtre par un view.dispose() je crois.
... même en appelant dispose (et je réponds aussi à SL qui m'a orienté

sur la même piste) dans :

public void dispose() {
image.flush();
image = null;
setVisible(false);
super.dispose();
}

puis
view = null;
System.gc();

ça ne va pas mieux.

Je vais regarder avec un profiler et ne pas recréer à chaque fois une
JFrame.

Merci pour l'aide en tout cas.

--
Olivier
This space for sale.

Avatar
oliv
Libert Sébastien wrote:
Tu trouveras sur http://mindprod.com/jgloss/dispose.html un petit résumé des
bonnes habitudes pour bien libérer des (J)Frame.
En gros, il conseille surtout de redéfinir dispose et de bien penser à tout
libérer (listeners, etc.)
Merci mais dispose() n'a pas suffi. En fait, comme les images sont

traitées successivement, j'ai laissé tomber l'approche 1 view / 1
image : je crée une seule view au début et je mets les images dedans.
Et ça a l'air de marcher...

De nouveau, pour ne rien oublier... hop un bon profiler ;-)
Oui, c'est l'occasion de me familiariser à ça surtout dans le contexte

d'un petit pgm tout simple.

Merci.

--
Olivier
This space for sale.