@ -338,6 +338,19 @@ public class ConcurrentReferenceHashMap<K, V> extends AbstractMap<K, V> implemen
}
}
}
}
/ * *
* Remove any entries that have been garbage collected and are no longer referenced .
* Under normal circumstances garbage collected entries are automatically purged as
* items are added or removed from the Map . This method can be used to force a purge ,
* and is useful when the Map is read frequently but updated less often .
* /
public void purgeUnreferencedEntries ( ) {
for ( Segment segment : this . segments ) {
segment . restructureIfNecessary ( false ) ;
}
}
@Override
@Override
public int size ( ) {
public int size ( ) {
int size = 0 ;
int size = 0 ;
@ -512,7 +525,7 @@ public class ConcurrentReferenceHashMap<K, V> extends AbstractMap<K, V> implemen
* references that have been garbage collected .
* references that have been garbage collected .
* @param allowResize if resizing is permitted
* @param allowResize if resizing is permitted
* /
* /
private void restructureIfNecessary ( boolean allowResize ) {
protected final void restructureIfNecessary ( boolean allowResize ) {
boolean needsResize = ( ( this . count > 0 ) & & ( this . count > = this . resizeThreshold ) ) ;
boolean needsResize = ( ( this . count > 0 ) & & ( this . count > = this . resizeThreshold ) ) ;
Reference < K , V > reference = this . referenceManager . pollForPurge ( ) ;
Reference < K , V > reference = this . referenceManager . pollForPurge ( ) ;
if ( ( reference ! = null ) | | ( needsResize & & allowResize ) ) {
if ( ( reference ! = null ) | | ( needsResize & & allowResize ) ) {
@ -550,7 +563,7 @@ public class ConcurrentReferenceHashMap<K, V> extends AbstractMap<K, V> implemen
restructured [ i ] = null ;
restructured [ i ] = null ;
}
}
while ( reference ! = null ) {
while ( reference ! = null ) {
if ( ! toPurge . contains ( reference ) ) {
if ( ! toPurge . contains ( reference ) & & ( reference . get ( ) ! = null ) ) {
int index = getIndex ( reference . getHash ( ) , restructured ) ;
int index = getIndex ( reference . getHash ( ) , restructured ) ;
restructured [ index ] = this . referenceManager . createReference (
restructured [ index ] = this . referenceManager . createReference (
reference . get ( ) , reference . getHash ( ) ,
reference . get ( ) , reference . getHash ( ) ,
@ -564,7 +577,7 @@ public class ConcurrentReferenceHashMap<K, V> extends AbstractMap<K, V> implemen
if ( resizing ) {
if ( resizing ) {
setReferences ( restructured ) ;
setReferences ( restructured ) ;
}
}
this . count = countAfterRestructure ;
this . count = Math . max ( countAfterRestructure , 0 ) ;
} finally {
} finally {
unlock ( ) ;
unlock ( ) ;
}
}
@ -974,6 +987,7 @@ public class ConcurrentReferenceHashMap<K, V> extends AbstractMap<K, V> implemen
enqueue ( ) ;
enqueue ( ) ;
clear ( ) ;
clear ( ) ;
}
}
}
}
@ -1007,6 +1021,7 @@ public class ConcurrentReferenceHashMap<K, V> extends AbstractMap<K, V> implemen
enqueue ( ) ;
enqueue ( ) ;
clear ( ) ;
clear ( ) ;
}
}
}
}
}
}