Ik had net een interview, en er werd me gevraagd om een geheugenlek te maken met Java.
Onnodig te zeggen dat ik me behoorlijk dom voelde omdat ik geen idee had hoe ik er een moest maken.
Wat zou een voorbeeld zijn?
Een eenvoudige manier is om een HashSet te gebruiken met een onjuiste (of niet-bestaande) hashCode()
of equals()
, en dan "duplicates" te blijven toevoegen. In plaats van duplicaten te negeren zoals het hoort, zal de set alleen maar groeien en je zult'niet in staat zijn om ze te verwijderen.
Als je wilt dat deze slechte sleutels/elementen blijven hangen kun je een statisch veld gebruiken zoals
class BadKey {
// no hashCode or equals();
public final String key;
public BadKey(String key) { this.key = key; }
}
Map map = System.getProperties();
map.put(new BadKey("key"), "value"); // Memory leak even if your threads die.
Misschien door externe native code te gebruiken via JNI?
Met pure Java, is het bijna onmogelijk.
Maar dat gaat over een "standard" type geheugenlek, wanneer je geen toegang meer hebt tot het geheugen, maar het is nog steeds eigendom van de applicatie. Je kunt in plaats daarvan referenties naar ongebruikte objecten bewaren, of streams openen zonder ze daarna te sluiten.
Maak een statische Map en blijf er harde referenties aan toevoegen. Die zullen nooit GC'd worden.
public class Leaker {
private static final Map<String, Object> CACHE = new HashMap<String, Object>();
// Keep adding until failure.
public static void addToCache(String key, Object value) { Leaker.CACHE.put(key, value); }
}