WeakHashMap
WeakHashMap
is one of the lesser known member of Map family. It is a special kind
of hashtable based Map implementation which stores weak references to
the keys. That means keys of this kind of data structure will be
stored in a WeakReference . So Entry of the Map will be reclaimed by
the garbage collector when its key object is no longer used. More
precisely, the presence of a mapping for a given key will not prevent
the key from being discarded by the garbage collector, that is, made
finalizable, finalized, and then reclaimed.
In
HashMap , if reference of a key object no longer exist ,
corresponding Entry ( key – value pair ) will not be removed from
Map . Garbage collector can not collect live objects . As long as Map
object is live , all buckets or Entry are live . So they can not be
collected by garbage collector .
WeakHashMap
uses a weak references of object to hold a key . Entry inner class of
WeakHashMap extends WeakReference to implement weak reference of key
object .
private
static
class
Entry<K, V>
extends
WeakReference<Object>
implements
Map.Entry<K, V>
{
V
value;
int
hash;
Entry<K, V>
next;
....
}
Garbage
collector treats this kind of object n special way . Normally garbage
collector reclaims an object if garbage collector finds that
particular object has no reference to it . But if Object is only
reachable by weak reference , garbage collector still reclaimes the
same , but places the weak reference that led to into queue . It
periodically goes on checking the queue for newly arrieved weak
references . Arrival of new weak references in queue signifies that
the key was no longer used by anyone and has been collected . The
WeakHashMap then removes the stale entry .
WeakHashMap
has a private method expungeStaleEntries()
. It is used to remove stale entries from Map . This method is used
internally from getTable() , size() , resize() methods .
private
void
expungeStaleEntries()
{
Reference
localReference;
while
((localReference
= queue.poll())
!= null)
{
synchronized
(queue)
{
Entry localEntry1
= (Entry)localReference;
int
i =
indexFor(hash,
table.length);
Object localObject1
= table[i];
Entry localEntry2;
for
(Object localObject2
= localObject1;
localObject2
!= null;
localObject2
= localEntry2)
{
localEntry2
= next;
if
(localObject2
== localEntry1)
{
if
(localObject1
== localEntry1)
{
table[i]
= localEntry2;
} else
{
next =
localEntry2;
}
value = null;
size
-= 1;
break;
}
localObject1
= localObject2;
}
}
}
}
This
method keep polling queue for new entry and removes the associated
entry if new object found .
Comments
Post a Comment