THE Java™ Programming Language, Fourth Edition

(Jeff_L) #1

strong references becomes unreachable when it is no longer strongly reachable.


The reachability stages of an object trigger behavior in the garbage collector appropriate to the corresponding
reference object types:


A softly reachable object may be reclaimed at the discretion of the garbage collector. If memory is
low, the collector may clear a SoftReference object so that its referent can be reclaimed. There
are no specific rules for the order in which this is done (but a good implementation will prefer keeping
recently used or created references, where "used" is defined as "invoked get"). You can be sure that
all SoftReferences to softly reachable objects will be cleared before an OutOfMemoryError
is thrown.


A weakly reachable object will be reclaimed by the garbage collector. When the garbage collector
determines that an object is weakly reachable, all WeakReference objects that refer to that object
will be cleared. The object then becomes finalizable and after finalization will be reclaimed (assuming
it is not resurrected) unless it is phantom reachable.


A phantom reachable object isn't really reachable in the normal sense because the referent object
cannot be accessed via a PhantomReferenceget always returns null. But the existence of the
phantom reference prevents the object from being reclaimed until the phantom reference is explicitly
cleared. Phantom references allow you to deal with objects whose finalize methods have been
invoked and so can safely be considered "dead." Phantom references are used in conjunction with the
reference queues we discuss in the next section.


Both SoftReference and WeakReference declare a constructor that takes a single referent object. All
three classes declare a two-argument constructor that takes a referent object and a ReferenceQueue.


Soft references provide you with a kind of caching behavior, clearing older references while trying not to clear
new or used ones. Consider our web browser scenario. If you maintain your images in soft references, they
will be reclaimed as memory runs low. Images are probably relatively unimportant to keep in memory should
memory run low, and clearing the oldest or least used images would be a reasonable approach. In contrast, if
you used weak references then all images would be reclaimed as soon as memory got lowthis would probably
induce a lot of overhead as you reload images that it may not have been necessary to get rid of in the first
place.


Weak references are a way of holding a reference to an object but saying "reclaim this object if this is the only
type of reference to it."


Consider the following method that returns data read into memory from a file. The method has been optimized
under the assumption that the same file is often named more than once in a row and that reading the data is
expensive:


import java.lang.ref.*;
import java.io.File;


class DataHandler {
private File lastFile; // last file read
private WeakReference<byte[]>
lastData; // last data (maybe)


byte[] readFile(File file) {
byte[] data;


// check to see if we remember the data
if (file.equals(lastFile)) {
data = lastData.get();
if (data != null)
return data;
}

Free download pdf