Q : Comment une fuite de mémoire peut-elle se produire en Java ?
R : En Java, les fuites de mémoire peuvent avoir de nombreuses causes. Un exemple typique est un code qui n'implémente pas hasCode et
La classe Key de la méthode égale est enregistrée dans HashMap. Au final, de nombreux objets en double seront générés. Toutes les fuites de mémoire
Au final, une exception OutOfMemoryError sera levée. Voici une brève simulation d'une fuite de mémoire via une boucle infinie.
Expliquez avec un exemple.
Copiez le code comme suit :
importer java.util.HashMap ;
importer java.util.Map ;
classe publique MemoryLeak {
public static void main (String[] arguments) {
Map<Key, String> map = new HashMap<Key, String>(1000);
compteur int = 0 ;
tandis que (vrai) {
// crée des objets en double en raison d'une mauvaise classe Key
map.put(new Key("dummyKey"), "value");
compteur++;
si (compteur % 1000 == 0) {
System.out.println("taille de la carte : " + map.size());
System.out.println("Mémoire libre après le décompte " + compteur
+ " est " + getFreeMemory() + "Mo");
dormir (1000);
}
}
}
// Clé de classe interne sans hashcode() ou equals() -- mauvaise implémentation
Clé de classe statique {
clé de chaîne privée ;
Clé publique (clé de chaîne) {
this.key = clé ;
}
}
//délai pour une période donnée en millisecondes
public static void sleep (long sleepFor) {
essayer {
Thread.sleep(sleepFor);
} catch (InterruptedException e) {
e.printStackTrace();
}
}
//récupère la mémoire disponible en Mo
public statique long getFreeMemory() {
return Runtime.getRuntime().freeMemory() / (1024 * 1024);
}
}
Le résultat est le suivant :
Copiez le code comme suit :
taille de la carte : 1000
La mémoire libre après 1 000 comptes est de 4 Mo.
taille de la carte : 2000
La mémoire libre après le compte 2000 est de 4 Mo
taille de la carte : 1396000
La mémoire libre après le compte 1396000 est de 2 Mo
taille de la carte : 1397000
La mémoire libre après le compte 1397000 est de 2 Mo
taille de la carte : 1398000
La mémoire libre après le compte 1398000 est de 2 Mo
taille de la carte : 1399000
La mémoire libre après le compte 1399000 est de 1 Mo
taille de la carte : 1 400 000
La mémoire libre après le compte 1 400 000 est de 1 Mo.
taille de la carte : 1401000
La mémoire libre après le compte 1401000 est de 1 Mo
.....
.....
taille de la carte : 1452000
La mémoire libre après le compte 1452000 est de 0 Mo
taille de la carte : 1453000
La mémoire libre après le compte 1453000 est de 0 Mo
Exception dans le thread "main" java.lang.OutOfMemoryError : espace de tas Java
sur java.util.HashMap.addEntry(HashMap.java:753)
sur java.util.HashMap.put(HashMap.java:385)
sur MemoryLeak.main (MemoryLeak.java:10)
Q : Comment résoudre la fuite de mémoire ci-dessus ?
R : Implémentez les méthodes equals et hasCode de la classe Key.
Copiez le code comme suit :
.....
Clé de classe statique {
clé de chaîne privée ;
Clé publique (clé de chaîne) {
this.key = clé ;
}
@Outrepasser
public booléen égal (Objet obj) {
si (instance obj de clé)
return key.equals(((Key) obj).key);
autre
renvoie faux ;
}
@Outrepasser
public int hashCode() {
return key.hashCode();
}
}
.....
La réexécution du programme donnera les résultats suivants :
Copiez le code comme suit :
taille de la carte : 1
La mémoire libre après 1 000 comptes est de 4 Mo.
taille de la carte : 1
La mémoire libre après le compte 2000 est de 4 Mo
taille de la carte : 1
La mémoire libre après le compte 3000 est de 4 Mo
taille de la carte : 1
La mémoire libre après le compte 4000 est de 4 Mo
...
La mémoire libre après le compte 73 000 est de 4 Mo
taille de la carte : 1
La mémoire libre après le compte 74 000 est de 4 Mo
taille de la carte : 1
La mémoire libre après le compte 75 000 est de 4 Mo
Q : Dans des scénarios réels, comment détectez-vous les fuites de mémoire ?
R : Obtenez l’ID du fil via le code suivant
Copiez le code comme suit :
C:/>jps
5808Jps
4568 Fuite de mémoire
3860 Principale
Ouvrez jconsole via la ligne de commande
Copiez le code comme suit :
C:/>jconsole 4568
La classe Key qui implémente hasCode et equals et le graphique qui ne l'implémente pas sont les suivants :
Aucune fuite de mémoire :
Cause d'une fuite de mémoire :