偶然查找代碼的時候發(fā)現(xiàn)tomcat中有一個ConcurrentCache類吓揪。并發(fā)?緩存若皱?我感興趣的點了進去镊叁。
功能描述:用于緩存數(shù)據(jù),數(shù)據(jù)量超過size可能過期舊數(shù)據(jù)走触。
代碼挺簡單的晦譬,其中eden為熱點數(shù)據(jù),longterm為長期數(shù)據(jù)饺汹,size為緩存大小蛔添。
- 添加數(shù)據(jù)(put)添加到eden痰催,超過緩存大小后將eden中的數(shù)據(jù)全部轉(zhuǎn)移至longterm兜辞。此時在eden中沒有兒longterm有的數(shù)據(jù),由于是弱引用的夸溶,會在GC時回收掉逸吵。
- 獲取緩存(get)會先從eden中查找,沒有數(shù)據(jù)再去查詢longterm缝裁,如果longterm中有數(shù)據(jù)扫皱,則重新設(shè)置為熱點數(shù)據(jù)(eden)。
完整代碼:
public final class ConcurrentCache<K, V> {
private final int size;
private final Map<K, V> eden;
private final Map<K, V> longterm;
public ConcurrentCache(int size) {
this.size = size;
this.eden = new ConcurrentHashMap(size);
this.longterm = new WeakHashMap(size);
}
public V get(K k) {
V v = this.eden.get(k);
if (v == null) {
synchronized(this.longterm) {
v = this.longterm.get(k);
}
if (v != null) {
this.eden.put(k, v);
}
}
return v;
}
public void put(K k, V v) {
if (this.eden.size() >= this.size) {
synchronized(this.longterm) {
this.longterm.putAll(this.eden);
}
this.eden.clear();
}
this.eden.put(k, v);
}
}