Pourquoi est-ce une mauvaise pratique d'appeler le système.gc ()?

après répondant à une question sur la façon de objets sans force en Java (le gars était en train de nettoyer un HashMap de 1,5 Go) avec System.gc() , on m'a dit que c'était une mauvaise pratique d'appeler System.gc() manuellement, mais les commentaires n'étaient pas entièrement convaincants. En outre, personne n'a semblé oser monter ou descendre ma réponse.

on m'a dit que c'était une mauvaise pratique, mais on m'a aussi dit que le ramasseur d'ordures ne fonctionne pas systématiquement arrêter le monde plus, et qu'il pourrait également être effectivement utilisé par la JVM que comme un indice, donc je suis un peu à côté de la plaque.

je comprends que le JVM sait généralement mieux que vous quand il a besoin de récupérer la mémoire. Je comprends aussi que s'inquiéter de quelques kilo-octets de données est stupide. Je comprends aussi que même mégaoctets de données n'est pas ce qu'il était quelques années en arrière. Mais quand même, 1,5 gigaoctets? Et vous savoir il y a comme 1,5 Go de des données qui traînent dans la mémoire; ce n'est pas comme si c'était un tir dans le noir. Est-ce que System.gc() est systématiquement mauvais, ou y a-t-il un moment où cela devient acceptable?

donc la question Est en fait double:

  • Pourquoi est-ce une mauvaise pratique d'appeler System.gc() ? S'agit-il vraiment d'une simple allusion à la JVM sous certaines implémentations, ou s'agit-il toujours d'un cycle complet de collecte? Est-ce qu'il y a vraiment des implémentations de ramasseur de déchets qui peuvent faire leur travailler sans arrêter le monde? S'il vous plaît, éclairez-moi sur les différentes affirmations que les gens ont faites dans les commentaires à ma réponse .
  • Où est le seuil? Est-ce que jamais est une bonne idée d'appeler System.gc() , ou y a-t-il des moments où c'est acceptable? Si oui, quelles sont ces moments?
289
demandé sur Community 2010-03-10 05:19:38

13 réponses

la raison pour laquelle tout le monde dit toujours d'éviter System.gc() est qu'il est un assez bon indicateur de code fondamentalement cassé . Tout code qui dépend de lui pour être correct est certainement cassé; tous ceux qui dépendent de lui pour être performant sont très probablement cassés.

vous ne savez pas sous quel genre de collecteur d'ordures vous êtes. Il y en a certainement qui ne font pas "stop the world" comme vous le dites, mais quelques JVM n'est-ce pas intelligent ou pour diverses raisons (peut-être sont-ils sur un téléphone? ne pas le faire. Vous ne savez pas ce qu'il va faire.

aussi, il n'est pas garanti de faire quoi que ce soit. La JVM peut tout simplement ignorer votre demande.

La combinaison de "tu ne sais pas ce qu'il va faire", "tu ne sais pas si il va même jusqu'à les aider," et "vous ne devriez pas avoir besoin de l'appeler de toute façon" sont pourquoi les gens sont tellement énergique en disant que, généralement, vous ne devez pas appeler. Je pense que c'est un cas de" si vous avez besoin de demander si vous devez utiliser ceci, vous ne devriez pas "


éditer pour répondre à quelques préoccupations de l'autre fil:

après avoir lu le fil que vous avez relié, il y a quelques autres choses que j'aimerais souligner. Tout d'abord, quelqu'un a suggéré que l'appel gc() pourrait rendre la mémoire au système. Ce n'est certainement pas nécessairement vrai - le tas de Java lui-même se développe indépendamment de Allocations Java.

comme dans, le JVM gardera la mémoire (plusieurs dizaines de mégaoctets) et augmentera le tas si nécessaire. Il ne renvoie pas nécessairement cette mémoire au système même lorsque vous libérez des objets Java; il est parfaitement libre de s'accrocher à la mémoire allouée à utiliser pour de futures attributions Java.

pour montrer qu'il est possible que System.gc() ne fait rien, voir:

http://bugs.sun.com/view_bug.do?bug_id=6668279

et en particulier qu'il y a une option - XX:Disablexplicitgc VM.

224
répondu Steven Schlansker 2014-12-12 10:55:00

il a déjà été expliqué qu'appeler system.gc() peut ne rien faire, et que tout code qui" a besoin " du collecteur d'ordures pour fonctionner est cassé.

cependant, la raison pragmatique pour laquelle il est de mauvaise pratique d'appeler System.gc() est qu'il est inefficace. Et dans le pire des cas, c'est horriblement inefficace ! Laissez-moi vous expliquer.

un algorithme typique de GC identifie les ordures par en traversant tous les objets qui ne sont pas des déchets dans le tas, et en déduisant que tout objet non visité doit être des déchets. À partir de cela, nous pouvons modéliser le travail total d'une collecte de déchets, qui comprend une partie qui est proportionnelle à la quantité de données vivantes, et une autre partie qui est proportionnelle à la quantité de déchets, c.-à-d. work = (live * W1 + garbage * W2) .

supposez maintenant que vous faites ce qui suit dans une application mono-filetée.

System.gc(); System.gc();

le premier appel sera (nous prédire) faire (live * W1 + garbage * W2) travail, et se débarrasser des ordures en suspens.

Le second appel se faire (live* W1 + 0 * W2) travail et récupérer de rien. En d'autres termes, nous avons fait (live * W1) travail et atteint absolument rien .

nous pouvons modéliser l'efficacité du collecteur comme la quantité de travail nécessaire pour collecter une unité de déchets; i.e. efficiency = (live * W1 + garbage * W2) / garbage . Ainsi, pour rendre le GC aussi efficace que possible, nous avons besoin de maximiser la valeur de garbage lorsque nous exécutons le CG; c.-à-d. attendre jusqu'à ce que le tas soit plein. (Et aussi, faire le tas aussi grand que possible. Mais c'est un autre sujet.)

si l'application n'interfère pas (en appelant System.gc() ), le GC attendra que le tas soit plein avant de lancer, ce qui se traduira par une collecte efficace des ordures 1 . Mais si l'application force le GC à courir, les chances sont que le tas ne sera pas complet, et le résultat sera que les ordures sont collectées de façon inefficace. Et plus souvent L'application force le GC, plus le GC devient inefficace.

Note: l'explication ci-dessus passe sous silence le fait qu'un GC moderne typique divise le tas en "espaces", le GC peut dynamiquement étendre le tas, l'ensemble de travail de l'application des objets non-ordures peut varier et ainsi de suite. Même ainsi, le même principe de base s'applique à tous les véritables éboueurs. 2 . Il est inefficace de forcer le GC à s'exécuter.


1 - C'est ainsi que fonctionne le collecteur" throughput". Les collecteurs concurrents tels que CMS et G1 utilisent des critères différents pour décider quand démarrer le collecteur d'ordures.

2-j'exclus Aussi les gestionnaires de mémoire qui utilisent exclusivement le comptage de référence, mais aucune implémentation Java actuelle n'utilise cette approche ... pour une bonne raison.

134
répondu Stephen C 2018-05-16 21:18:12

beaucoup de gens semblent vous dire de ne pas le faire. Je suis en désaccord. Si, après un grand processus de chargement comme le chargement d'un niveau, vous croyez que:

  1. vous avez beaucoup d'objets qui sont inaccessibles et peut-être pas gc'ed. et
  2. Vous pensez que l'utilisateur peut mettre en place avec un petit ralentissement à ce point

il n'y a pas de mal à Système d'appel.gc (). Je la regarde comme le c/c++ inline mot. C'est juste une indication au gc que vous, le développeur, avez décidé que le temps/la performance n'est pas aussi important qu'il l'est habituellement et que certains d'entre eux pourraient être utilisés pour récupérer de la mémoire.

le Conseil de ne pas s'y fier est correct. Ne vous fiez pas au travail, mais donner l'indication que maintenant est un temps acceptable pour collecter est parfaitement bien. Je préfère perdre du temps à un point dans le code où il n'a pas d'importance (écran de chargement) que lorsque l'utilisateur est en interagir avec le programme (comme pendant un niveau d'un jeu.)

il y a une fois où je vais force collection: lorsque je tente de découvrir est un objet particulier fuites (soit code natif ou grande, complexe interaction de rappel. Oh et n'importe quel composant de L'interface qui jette un coup d'oeil à Matlab.) ceci ne doit jamais être utilisé dans le code de production.

42
répondu KitsuneYMG 2012-10-10 13:48:53

les gens ont fait un bon travail en expliquant pourquoi ne pas utiliser, donc je vais vous dire quelques situations où vous devriez l'utiliser:

(les commentaires suivants s'appliquent à un Hotspot tournant sur Linux avec le CMS collector, où je me sens confiant en disant que System.gc() fait en fait toujours appel à une collecte des ordures complète).

  1. après le travail initial de démarrage de votre application, vous pouvez être un État de mémoire terrible utilisation. La moitié de votre génération peut être remplie de déchets, ce qui signifie que vous êtes beaucoup plus près de votre premier SGC. Dans les applications où qui compte, c'est pas une mauvaise idée d'appeler Système.gc() pour "reset" de votre tas à l'état de départ des données en direct.

  2. dans le même esprit que #1, si vous surveillez étroitement votre utilisation de tas, vous voulez avoir une lecture précise de ce que votre utilisation de base de mémoire est. Si les 2 premières minutes de votre application la disponibilité est l'initialisation, vos données vont être foiré, sauf si vous forcez (ahem... "suggest") le gc complet à l'avance.

  3. vous pouvez avoir une application qui est conçue pour ne jamais promouvoir quoi que ce soit à la génération titulaire pendant qu'il est en cours d'exécution. Mais peut-être que vous avez besoin d'initialiser certaines données à l'avance qui n'est pas si énorme que de se déplacer automatiquement à la génération titulaire. Sauf si vous appelez le système.gc() après tout est mis en place, vos données pourraient asseyez-vous dans la nouvelle génération jusqu'à ce que le moment soit venu pour elle d'être promue. Tout d'un coup, votre application super-duper low-latency, low-GC est frappée d'une énorme (relativement parlant, bien sûr) pénalité de latence pour la promotion de ces objets pendant les opérations normales.

  4. il est parfois utile d'avoir un système.appel gc disponible dans une application de production pour vérifier l'existence d'une fuite de mémoire. Si vous savez que l'ensemble des données en direct au moment X existent dans un certain rapport à l'ensemble des données en direct au moment de Y, alors il pourrait être utile d'appeler Système.gc () un temps X et un temps Y et comparez l'utilisation de la mémoire.

26
répondu JT. 2011-02-09 14:13:47

efficacité GC repose sur un certain nombre d'heuristiques. Par exemple, une heuristique commune est que les accès d'écriture à des objets se produisent habituellement sur des objets qui ont été créés il n'y a pas longtemps. Un autre est que de nombreux objets sont de très courte durée (quelques objets seront utilisés pendant une longue période, mais beaucoup seront jetés quelques microsecondes après leur création).

appeler System.gc() c'est comme donner un coup de pied au GC. Cela signifie: "tous ces paramètres soigneusement ajustés, ces organisations intelligentes, tous les efforts que vous venez de mettre dans l'allocation et la gestion des objets de sorte que les choses se passent bien, eh bien, tout simplement laisser tomber le tout, et de commencer à partir de zéro". Il mai améliorer la performance, mais la plupart du temps, il est juste dégrader la performance.

pour utiliser System.gc() de manière fiable(*) vous devez savoir comment le GC fonctionne dans tous ses détails. Ces détails ont tendance à changer beaucoup si vous utilisez une JVM d'un autre fournisseur, ou le suivant version du même fournisseur, ou de la même JVM mais avec des options de ligne de commande légèrement différentes. Donc, c'est rarement une bonne idée, sauf si vous voulez répondre à un problème spécifique dans lequel vous contrôlez tous ces paramètres. D'où la notion de "mauvaise pratique": ce n'est pas interdit, la méthode existe, mais elle porte rarement ses fruits.

( * ) je parle ici d'efficacité. System.gc() ne sera jamais break un programme Java correct. Il ne fera pas apparaître de mémoire supplémentaire que la JVM n'aurait pas pu obtenir autrement: avant de lancer un OutOfMemoryError , la JVM fait le travail de System.gc() , même en dernier recours.

9
répondu Thomas Pornin 2010-03-10 16:25:08

parfois ( pas souvent! ) vous en savez vraiment plus sur l'utilisation passée, actuelle et future de la mémoire que le temps d'exécution. Cela ne se produit pas très souvent, et je ne prétends jamais dans une application web pendant que les pages normales sont servies.

il y a de nombreuses années je travaille sur un générateur de rapport ,que

  • avait un seul filetage
  • Lire "demande de rapport" à partir d'une file d'attente
  • Chargé les données nécessaires pour le rapport de la base de données
  • a généré le rapport et l'a envoyé.
  • répété pour toujours, endormi quand il n'y avait pas de demandes en suspens.
  • il n'a pas réutilisé de données entre les rapports et n'a pas fait d'encaissement.

tout D'abord parce que ce n'était pas en temps réel et que les utilisateurs s'attendaient à un rapport, un retard alors que L'exécution du GC n'était pas un problème, mais nous avons dû produire rapports à un rythme plus rapide que ce qui avait été demandé.

en examinant les grandes lignes ci-dessus du processus, il est clair que.

  • nous savons qu'il y aurait très peu d'objets vivants juste après qu'un rapport ait été envoyé, car la prochaine demande n'avait pas encore commencé à être traitée.
  • il est bien connu que le coût de fonctionnement d'un cycle de collecte des ordures dépend du nombre d'objets vivants, la quantité de déchets a peu d'effet sur le coût d'un GC exécuter.
  • que lorsque la file d'attente est vide, il n'y a rien de mieux à faire, puis exécuter le CG.

par conséquent, il était évident que cela valait la peine de faire un essai GC chaque fois que la file d'attente des requêtes était vide; il n'y avait aucun inconvénient à cela.

il vaut peut-être la peine de faire une course GC après l'envoi de chaque rapport, car nous savons que c'est un bon moment pour une course GC. Toutefois, si l'ordinateur avait suffisamment de mémoire vive, de meilleurs résultats seraient obtenus en retardant l'exécution de L'essai GC.

ce comportement a été configuré sur des bases d'installation per, pour certains clients permettant un GC forcé après chaque rapport grandement accéléré la protection des rapports. (Je m'attends à ce que ce soit dû à la mémoire faible sur leur serveur et il exécute beaucoup d'autres processus, donc un temps bien forcé GC réduit la pagination.)

nous n'avons jamais détecté une installation qui n'en a pas bénéficié a été un passage forcé au GC chaque fois que la file d'attente de travail était vide.

mais, soyons clairs, ce qui précède n'est pas un cas courant.

5
répondu Ian Ringrose 2014-09-29 13:27:27

C'est une question très gênante, et je pense que cela contribue à ce que beaucoup soient opposés à Java malgré l'utilité d'un langage.

Le fait que vous ne pouvez pas faire confiance "le Système de.gc" de faire quelque chose est colossale et peut facilement appeler "la Peur, l'Incertitude, le Doute" se sentir à la langue.

dans de nombreux cas, il est agréable de traiter avec des pointes de mémoire que vous causez exprès avant qu'un événement important se produit, ce qui amènerait les utilisateurs à penser votre le programme est mal conçu / ne répond pas.

avoir la capacité de contrôler la collecte des ordures serait un très bon outil d'éducation, à son tour améliorer la compréhension des gens comment la collecte des ordures fonctionne et comment faire des programmes exploiter son comportement par défaut ainsi que le comportement contrôlé.

permettez-moi de passer en revue les arguments de ce fil.

  1. Il est inefficace:

souvent, le le programme ne fait peut-être rien et vous savez qu'il ne fait rien à cause de la façon dont il a été conçu. Par exemple, il pourrait faire une sorte de longue attente avec une grande boîte de message d'attente, et à la fin, il peut aussi bien ajouter un appel à ramasser les ordures parce que le temps de l'exécuter prendra une très petite fraction du temps de la longue attente, mais évitera gc d'agir au milieu d'une opération plus importante.

  1. il est toujours une mauvaise pratique et indique un code brisé.

je suis en désaccord, il n'a pas d'importance ce que garbage collector que vous avez. Son travail est de pister les ordures et de les nettoyer.

en appelant le gc pendant les périodes où l'utilisation est moins critique, vous réduisez les chances qu'il tourne lorsque votre vie dépend du code spécifique étant exécuté, mais plutôt il décide de ramasser les ordures.

bien sûr, il pourrait ne pas se comporter comme vous voulez ou attendez, mais quand vous voulez appeler il, vous savez que rien ne se passe, et l'utilisateur est prêt à tolérer la lenteur / temps d'arrêt. Si le système.gc fonctionne, tant mieux! Si ce n'est pas le cas, au moins tu as essayé. Il n'y a tout simplement aucun côté négatif à moins que le collecteur d'ordures ait des effets secondaires inhérents qui font quelque chose d'horriblement inattendu à la façon dont un collecteur d'ordures est censé se comporter s'il est invoqué manuellement, et cela en soi provoque la méfiance.

  1. ce n'est pas un cas d'usage courant:

C'est un cas d'utilisation qui ne peut être atteint de façon fiable, mais qui pourrait l'être si le système était conçu de cette façon. C'est comme faire un feu de circulation et le faire de sorte que certains/tous les boutons des feux de circulation ne font rien, il vous fait vous demandez pourquoi le bouton est là pour commencer, javascript n'a pas de fonction de collecte des ordures donc nous ne scrutez pas autant pour elle.

  1. la spécification dit que le système.gc () est une indication que GC devrait exécuter et que la VM est libre de l'ignorer.

qu'est ce qu'une "astuce"? qu'est-ce que "ignorer"? un ordinateur ne peut pas simplement prendre des indices ou ignorer quelque chose, Il ya des chemins de comportement strict qu'il prend qui peut être dynamique qui sont guidés par l'intention du système. Une réponse appropriée inclurait ce que le collecteur d'ordures fait réellement, au niveau de la mise en œuvre, qui fait qu'il n'effectue pas la collecte lorsque vous le demandez. La fonctionnalité est-elle simplement un nop? Y a-t-il des conditions que je dois remplir? Ce sont ces conditions?

tel qu'il est, le GC de Java semble souvent comme un monstre que vous ne faites tout simplement pas confiance. Tu ne sais pas quand ça va aller ou venir, tu ne sais pas ce que ça va faire, comment ça va le faire. Je peux imaginer que certains experts ont une meilleure idée de la façon dont leur collecte des ordures fonctionne sur la base de l'instruction, mais la grande majorité espère simplement que cela "fonctionne simplement", et avoir à faire confiance à un algorithme opaque semblant de faire le travail pour vous est frustrant.

Il y a un grand écart entre la lecture de quelque chose ou l'enseignement de quelque chose, et le fait de voir la mise en œuvre de celui-ci, les différences entre les systèmes, et d'être capable de jouer avec sans avoir à regarder le code source. Cela crée la confiance et le sentiment de maîtrise/compréhension / contrôle.

pour résumer, il y a un problème inhérent avec les réponses "cette fonctionnalité pourrait ne rien faire, et je ne vais pas entrer dans les détails comment dire quand il fait quelque chose et quand elle ne le fait pas et pourquoi elle ne le fait pas ou ne le fera pas, laissant souvent entendre qu'il est simplement contraire à la philosophie d'essayer de le faire, même si l'intention derrière elle est raisonnable".

C'est peut-être bien pour Java GC de se comporter comme il le fait, ou peut-être pas, mais pour le comprendre, il est difficile de vraiment suivre dans quelle direction aller pour obtenir un aperçu complet de ce que vous pouvez faire confiance au GC et de ne pas le faire, donc c'est trop facile tout simplement se méfier de la langue, parce que le but d'un langage est d'avoir un comportement contrôlé jusqu'à l'étendue philosophique(il est facile pour un programmeur, en particulier les novices de tomber dans la crise existentielle de certains comportements de système/langue) vous êtes capable de tolérer(et si vous ne pouvez pas, vous ne serez tout simplement pas utiliser la langue jusqu'à ce que vous le DEVEZ), et plus de choses que vous ne pouvez pas contrôler pour aucune raison connue pourquoi vous ne pouvez pas les contrôler est intrinsèquement nuisible.

5
répondu Dmitry 2016-06-30 00:14:09

peut-être que j'écris du code merdique, mais je me suis rendu compte que cliquer sur l'icône de la corbeille sur eclipse et netbeans IDEs est une 'bonne pratique'.

2
répondu Ryan Fernandes 2010-03-10 09:09:53

D'abord, il y a une différence entre le spec et la réalité. La spécification dit que Système.gc () est une indication que GC devrait exécuter et que la VM est libre de l'ignorer. La réalité est, la VM va jamais ignorer un appel au système.gc ().

appeler GC est livré avec un non-trivial overhead à l'appel et si vous le faites à un moment au hasard dans le temps, il est probable que vous ne verrez aucune récompense pour vos efforts. D'autre part, naturellement déclenché collection est très susceptible de récupérer les coûts de l'appel. Si vous avez des informations indiquant qu'un GC doit être exécuté que vous pouvez faire l'appel Système.gc() et vous devriez voir les avantages. Cependant, il est mon expérience que cela se produit seulement dans quelques cas de bord car il est très peu probable que vous aurez assez d'informations pour comprendre si et quand Système.gc () devrait être appelé.

un exemple énuméré ici, frapper la poubelle dans votre IDE. Si tu vas à une réunion, pourquoi ne pas y aller. Le les frais généraux ne vous affecteront pas et il se peut qu'on nettoie le tas à votre retour. Faire cela dans un système de production et des appels fréquents à collecter l'amènera à un arrêt de broyage! Même des appels occasionnels comme ceux de RMI peuvent perturber le rendement.

2
répondu Kirk 2013-09-02 10:29:01

Oui, Système d'appel.gc () ne garantit pas qu'il fonctionnera, c'est une requête à la JVM qui peut être ignorée. Extrait du docs:

appelant la méthode gc suggère que la machine virtuelle Java dépense des efforts pour recycler les objets inutilisés

il est presque toujours une mauvaise idée de l'appeler parce que la gestion automatique de la mémoire sait généralement mieux que vous quand à gc. Il le fera lorsque sa réserve interne de la mémoire est faible, ou si L'OS demande qu'une certaine mémoire soit rendue.

il pourrait être acceptable d'appeler le système.gc() si vous savoir qu'elle aide. Par cela je veux dire que vous avez soigneusement testé et mesuré le comportement des deux scénarios sur la plate-forme de déploiement , et vous pouvez montrer que cela aide. Soyez conscient cependant que le gc n'est pas facilement prévisible - il peut aider sur une course et blesser sur une autre.

1
répondu tom 2010-03-10 02:34:37

d'après mon expérience, en utilisant le système.gc () est en fait une forme d'optimisation propre à la plate-forme (où "plate-forme" est la combinaison de l'architecture matérielle, de L'OS, de la version JVM et d'éventuels paramètres d'exécution tels que la mémoire vive disponible), parce que son comportement, bien que prévisible sur une plate-forme spécifique, peut (et va) varier considérablement d'une plate-forme à l'autre.

Oui, il y a sont les situations où le Système.le gc () s'améliorera (perception) performance. L'exemple est si des délais sont acceptables dans certaines parties de votre application, mais pas dans d'autres (le jeu de l'exemple cité ci-dessus, où vous voulez GC pour arriver au début d'un niveau, pas le niveau).

Cependant, si elle va aider ou blesser (ou ne rien faire) est très dépend de la plate-forme (tel que défini ci-dessus).

donc je pense qu'il est valide comme une optimisation de dernier recours plate-forme spécifique (i.e. si d'autres performances les optimisations ne sont pas assez). Mais vous ne devriez jamais l'appeler simplement parce que vous croyez qu'il pourrait aider(sans repères spécifiques), parce que les chances sont qu'il ne sera pas.

0
répondu sleske 2010-09-17 10:56:02
  1. puisque les objets sont alloués dynamiquement en utilisant le nouvel opérateur,

    vous pourriez vous demander comment ces objets sont détruits et leur

    mémoire libérée pour une réallocation ultérieure.

  2. dans certaines langues, comme le C++, les objets affectés dynamiquement doivent manuellement publié par l'utilisation d'un opérateur d'effacement.

  3. Java prend un différent approche; il gère la désallocation pour vous automatiquement.
  4. la technique qui accomplit ceci s'appelle la collecte des ordures. Cela fonctionne comme ceci: quand aucune référence à un objet n'existe, cet objet est supposé ne plus être nécessaire, et la mémoire occupée par l'objet peut être récupérée. Il n'y a pas de besoin explicite de détruire des objets comme en C++.
  5. le ramassage des ordures N'a lieu que de façon sporadique (si tant est qu'il y en ait) au cours de la l'exécution de votre programme.
  6. il ne se produira pas simplement parce qu'un ou plusieurs objets existent qui sont n'est plus utilisé.
  7. en outre, différentes implémentations Java d'exécution prendront les diverses méthodes de collecte des ordures, mais pour la plupart, vous ne devrait pas avoir à y penser tout en écrivant vos programmes.
0
répondu Tanmay Delhikar 2017-07-22 18:31:03

mes 2 cents: je charge quelques dessins animés dans une activité et je les joue. - Je charger, jouer, jeu de l'imageview fond null, un à la fois. Si je sors de l'activité et puis je reviens rapidement, après 3 ou 4 fois la mémoire engagée grandit trop jusqu'à ce que j'obtienne une exception hors de la mémoire.

en appelant garbage collector explicitement après avoir défini imageview background à null, je vois sur le logcat Eclipse que la mémoire est suffisamment libre - et dans mon cas gc est en fait lancé - et je ne fais pas arrêter l'application plus.

il est évident que le système peut décider de reporter l'exécution de gc, mais si vous savez plus ou moins comment fonctionne un gc, vous pouvez faire confiance dans un cas comme le mien, il sera appelé dès que possible, pour la raison que le système Remarque la mémoire utilisée de plus en plus et app il est sur le point de demander plus au système. Je pense que cela fonctionne comme les conteneurs de bibliothèque C++ std: vous obtenez un peu de mémoire de départ et chaque fois que ce n'est pas assez, il double.

dire que si vous avez besoin de l'appeler c'est dû à code cassé ou mauvais est une façon dogmatique déraisonnable de répondre à moi: expecially si vous pouvez programmer dans un langage avec la gestion manuelle totale de la mémoire comme C++ et vous devez faire face à la limite des ressources sur un appareil mobile avec un langage comme java à la place, sans aucune chance de libérer la mémoire manuellement, vous pouvez rapidement penser à de nombreuses situations dans lesquelles il est nécessaire d'appeler gc explicitement, expecially où vous avez un traçant gc et pas une référence comptant un, tu le code est propre et bien fait.

-1
répondu Black Imp 2014-03-30 04:44:22