Voici un exemple légèrement différent, un avec des champs de type référence finaux plutôt que des variables locales de type valeur finale:
public class MyClass {
public final MyOtherObject obj;
}
Chaque fois que vous créez une instance de MyClass, vous créez une référence sortante à une instance de MyOtherObject, et le GC devra suivre ce lien pour rechercher des objets en direct.
La JVM utilise un algorithme GC mark-sweep, qui doit examiner toutes les références en direct dans les emplacements GC "racine" (comme tous les objets de la pile d'appels actuelle). Chaque objet vivant est «marqué» comme vivant, et tout objet auquel un objet vivant fait référence est également marqué comme vivant.
Une fois la phase de marquage terminée, le GC parcourt le tas, libérant de la mémoire pour tous les objets non marqués (et compactant la mémoire pour les objets vivants restants).
En outre, il est important de reconnaître que la mémoire de tas Java est partitionnée en une «jeune génération» et une «ancienne génération». Tous les objets sont initialement attribués à la jeune génération (parfois appelée «la crèche»). Comme la plupart des objets sont de courte durée, le GC est plus agressif pour libérer les déchets récents de la jeune génération. Si un objet survit à un cycle de collecte de la jeune génération, il est déplacé dans l'ancienne génération (parfois appelée «génération titulaire»), qui est traitée moins fréquemment.
Donc, du haut de ma tête, je vais dire "non, le modificateur 'final' n'aide pas le GC à réduire sa charge de travail".
À mon avis, la meilleure stratégie pour optimiser votre gestion de la mémoire en Java est d'éliminer les fausses références le plus rapidement possible. Vous pouvez le faire en attribuant «null» à une référence d'objet dès que vous avez fini de l'utiliser.
Ou, mieux encore, minimisez la taille de chaque portée de déclaration. Par exemple, si vous déclarez un objet au début d'une méthode de 1000 lignes, et si l'objet reste en vie jusqu'à la fermeture de la portée de cette méthode (la dernière accolade fermante), alors l'objet peut rester en vie beaucoup plus longtemps qu'en fait nécessaire.
Si vous utilisez de petites méthodes, avec seulement une douzaine de lignes de code, alors les objets déclarés dans cette méthode tomberont plus rapidement hors de portée, et le GC sera en mesure de faire l'essentiel de son travail dans un environnement beaucoup plus efficace. jeune génération. Vous ne voulez pas que les objets soient déplacés vers l'ancienne génération à moins que cela ne soit absolument nécessaire.