Des finaliseurs à la libération déterministe des ressources
Remplacez la finalisation par AutoCloseable et n'utilisez Cleaner qu'en solution de secours défensive.
@Override
protected void finalize() throws Throwable {
nativeHandle.release();
}
final class NativeResource implements AutoCloseable {
private static final Cleaner CLEANER = Cleaner.create();
private static final class State implements Runnable {
private final long handle;
State(long handle) {
this.handle = handle;
}
@Override
public void run() {
release(handle);
}
}
private final Cleaner.Cleanable cleanable;
NativeResource(long handle) {
cleanable = CLEANER.register(this, new State(handle));
}
@Override
public void close() {
cleanable.clean();
}
}
Déterministe
Try-with-resources libère les ressources à un moment connu.
Cycle de vie plus sûr
Évite la résurrection par finaliseur et les ordres imprévisibles.
Solution de secours défensive
Cleaner peut récupérer les ressources abandonnées sans redéfinir finalize().
Cleaner et l'obsolescence de la finalisation sont disponibles depuis JDK 9 (septembre 2017)
La finalisation est obsolète et vouée à être supprimée ; elle ne garantit ni une libération rapide ni un ordre fiable. Implémentez AutoCloseable afin que les appelants puissent libérer les ressources de façon déterministe avec try-with-resources. Pour les ressources abandonnées, Cleaner peut invoquer en dernier recours la même action de nettoyage idempotente ; cette action ne doit pas conserver de référence vers l'objet enregistré.