K
- the key typeV
- the value type@Internal(since="1.1.1") public class CacheLIRS<K,V> extends Object implements LoadingCache<K,V>
A scan resistant cache. It is meant to cache objects that are relatively costly to acquire, for example file content.
This implementation is multi-threading safe and supports concurrent access. Null keys or null values are not allowed. The map fill factor is at most 75%.
Each entry is assigned a distinct memory size, and the cache will try to use at most the specified amount of memory. The memory unit is not relevant, however it is suggested to use bytes as the unit.
This class implements an approximation of the the LIRS replacement algorithm invented by Xiaodong Zhang and Song Jiang as described in http://www.cse.ohio-state.edu/~zhang/lirs-sigmetrics-02.html with a few smaller changes: An additional queue for non-resident entries is used, to prevent unbound memory usage. The maximum size of this queue is at most the size of the rest of the stack. About 6.25% of the mapped entries are cold.
Internally, the cache is split into a number of segments, and each segment is an individual LIRS cache.
Accessed entries are only moved to the top of the stack if at least a number of other entries have been moved to the front (1% by default). Write access and moving entries to the top of the stack is synchronized per segment.
Modifier and Type | Class and Description |
---|---|
static class |
CacheLIRS.Builder<K,V>
A builder for the cache.
|
static interface |
CacheLIRS.EvictionCallback<K,V>
Listener for items that are evicted from the cache.
|
Constructor and Description |
---|
CacheLIRS(int maxEntries)
Create a new cache with the given number of entries, and the default
settings (an average size of 1 per entry, 16 segments, and stack move
distance equals to the maximum number of entries divided by 100).
|
Modifier and Type | Method and Description |
---|---|
V |
apply(K key)
Discouraged.
|
ConcurrentMap<K,V> |
asMap()
Returns a view of the entries stored in this cache as a thread-safe map.
|
void |
cleanUp()
Performs any pending maintenance operations needed by the cache.
|
boolean |
containsKey(Object key)
Check whether there is a resident entry for the given key.
|
Set<Map.Entry<K,V>> |
entrySet()
Get the entry set for all resident entries.
|
V |
get(K key)
Get the value, loading it if needed.
|
V |
get(K key,
Callable<? extends V> valueLoader)
Returns the value associated with
key in this cache, obtaining that value from
valueLoader if necessary. |
ImmutableMap<K,V> |
getAll(Iterable<? extends K> keys)
Returns a map of the values associated with
keys , creating or retrieving those values
if necessary. |
ImmutableMap<K,V> |
getAllPresent(Iterable<?> keys)
Returns a map of the values associated with
keys in this cache. |
int |
getAverageMemory()
Get the average memory used per entry.
|
V |
getIfPresent(Object key)
Get the value for the given key if the entry is cached.
|
long |
getMaxMemory()
Get the maximum memory to use.
|
int |
getMemory(K key)
Get the memory used for the given key.
|
V |
getUnchecked(K key)
Get the value, loading it if needed.
|
long |
getUsedMemory()
Get the currently used memory.
|
void |
invalidate(Object key)
Remove an entry.
|
void |
invalidateAll()
Remove all entries.
|
void |
invalidateAll(Iterable<?> keys)
Discards any cached values for keys
keys . |
boolean |
isEmpty() |
List<K> |
keys(boolean cold,
boolean nonResident)
Get the list of keys.
|
Set<K> |
keySet()
Get the set of keys for resident entries.
|
static <K,V> CacheLIRS.Builder<K,V> |
newBuilder()
Create a builder.
|
V |
peek(K key)
Get the value for the given key if the entry is cached.
|
void |
put(K key,
V value)
Add an entry to the cache.
|
V |
put(K key,
V value,
int memory)
Add an entry to the cache.
|
void |
putAll(Map<? extends K,? extends V> m)
Copies all of the mappings from the specified map to the cache.
|
void |
refresh(K key)
Re-load the value for the given key.
|
V |
remove(Object key)
Remove an entry.
|
void |
setAverageMemory(int averageMemory)
Set the average memory used per entry.
|
void |
setMaxMemory(long maxMemory)
Set the maximum memory this cache should use.
|
long |
size()
Get the number of resident entries.
|
int |
sizeHot()
Get the number of hot entries in the cache.
|
int |
sizeMapArray()
Get the length of the internal map array.
|
int |
sizeNonResident()
Get the number of non-resident entries in the cache.
|
CacheStats |
stats()
Returns a current snapshot of this cache's cumulative statistics.
|
public CacheLIRS(int maxEntries)
maxEntries
- the maximum number of entriespublic void invalidateAll()
invalidateAll
in interface Cache<K,V>
public boolean containsKey(Object key)
key
- the key (may not be null)public V peek(K key)
key
- the key (may not be null)public V put(K key, V value, int memory)
key
- the key (may not be null)value
- the value (may not be null)memory
- the memory used for the given entrypublic void put(K key, V value)
public V get(K key, Callable<? extends V> valueLoader) throws ExecutionException
Cache
key
in this cache, obtaining that value from
valueLoader
if necessary. No observable state associated with this cache is modified
until loading completes. This method provides a simple substitute for the conventional
"if cached, return; otherwise create, cache and return" pattern.
Warning: as with CacheLoader.load(K)
, valueLoader
must not return
null
; it may either return a non-null value or throw an exception.
get
in interface Cache<K,V>
ExecutionException
- if a checked exception was thrown while loading the valuepublic V getUnchecked(K key)
If there is an exception loading, an UncheckedExecutionException is thrown.
getUnchecked
in interface LoadingCache<K,V>
key
- the keyUncheckedExecutionException
public V get(K key) throws ExecutionException
get
in interface LoadingCache<K,V>
key
- the keyExecutionException
public void refresh(K key)
If there is an exception while loading, it is logged and ignored. This method calls CacheLoader.reload, but synchronously replaces the old value.
refresh
in interface LoadingCache<K,V>
key
- the key@Nullable public V getIfPresent(Object key)
getIfPresent
in interface Cache<K,V>
key
- the key (may not be null)public void invalidate(Object key)
invalidate
in interface Cache<K,V>
key
- the key (may not be null)public V remove(Object key)
key
- the key (may not be null)public void invalidateAll(Iterable<?> keys)
Cache
keys
.invalidateAll
in interface Cache<K,V>
public int getMemory(K key)
key
- the key (may not be null)public long getUsedMemory()
public void setMaxMemory(long maxMemory)
maxMemory
- the maximum size (1 or larger)public void setAverageMemory(int averageMemory)
averageMemory
- the average memory used (1 or larger)public int getAverageMemory()
public long getMaxMemory()
public Set<Map.Entry<K,V>> entrySet()
public int sizeNonResident()
public int sizeMapArray()
public int sizeHot()
public long size()
public List<K> keys(boolean cold, boolean nonResident)
cold
- if true, only keys for the cold entries are returnednonResident
- true for non-resident entriespublic CacheStats stats()
Cache
public static <K,V> CacheLIRS.Builder<K,V> newBuilder()
public ImmutableMap<K,V> getAllPresent(Iterable<?> keys)
Cache
keys
in this cache. The returned map will
only contain entries which are already present in the cache.getAllPresent
in interface Cache<K,V>
public ConcurrentMap<K,V> asMap()
LoadingCache
Note that although the view is modifiable, no method on the returned map will ever cause entries to be automatically loaded.
public void cleanUp()
Cache
public void putAll(Map<? extends K,? extends V> m)
Cache
put(k, v)
on this map once for each mapping from key
k
to value v
in the specified map. The behavior of this operation is undefined
if the specified map is modified while the operation is in progress.public ImmutableMap<K,V> getAll(Iterable<? extends K> keys) throws ExecutionException
LoadingCache
keys
, creating or retrieving those values
if necessary. The returned map contains entries that were already cached, combined with newly
loaded entries; it will never contain null keys or values.
Caches loaded by a CacheLoader
will issue a single request to
CacheLoader.loadAll(java.lang.Iterable<? extends K>)
for all keys which are not already present in the cache. All
entries returned by CacheLoader.loadAll(java.lang.Iterable<? extends K>)
will be stored in the cache, over-writing
any previously cached values. This method will throw an exception if
CacheLoader.loadAll(java.lang.Iterable<? extends K>)
returns null
, returns a map containing null keys or values,
or fails to return an entry for each requested key.
Note that duplicate elements in keys
, as determined by Object.equals(java.lang.Object)
, will
be ignored.
getAll
in interface LoadingCache<K,V>
ExecutionException
- if a checked exception was thrown while loading the value. (ExecutionException
is thrown even if
computation was interrupted by an InterruptedException
.)public V apply(K key)
LoadingCache
Function
interface; use LoadingCache.get(K)
or
LoadingCache.getUnchecked(K)
instead.public boolean isEmpty()
Copyright © 2010 - 2020 Adobe. All Rights Reserved