LRU缓存淘汰
LRU缓存淘汰是redis中的一种淘汰策略, 当内存大小不足以存放数据时, 此时存入新数据, 将删除较早存入的数据.
在dubbo中使用LRU来缓存 hostName.
在mysql中使用LRU来缓存 serverSideStatementCheckCache 和 serverSideStatementCache.
代码实现
1 2 3 4 5 6 7 8 9 10 11 12 13 14 15 16 17 18 19 20 21 22 23 24 25 26 27 28 29 30 31 32 33 34 35 36 37 38 39 40 41 42 43 44 45 46 47 48 49 50 51 52 53 54 55 56 57 58 59 60 61 62 63 64 65 66 67 68 69 70 71 72 73 74 75 76 77 78 79 80 81 82 83 84 85 86 87 88 89 90 91 92 93 94 95 96 97 98 99 100 101 102 103 104 105 106 107 108 109 110 111 112 113 114 115 116
| package com.ipaynow.tool.lru;
import java.util.LinkedHashMap; import java.util.Map; import java.util.concurrent.locks.Lock; import java.util.concurrent.locks.ReentrantLock;
public class LRULinkedHashMap<K, V> extends LinkedHashMap<K, V> {
private volatile int maxCapacity;
private static final int DEFAULT_MAX_CAPACITY = 1000;
private static final float DEFAULT_LOAD_FACTOR = 0.75f;
private final Lock lock = new ReentrantLock();
public LRULinkedHashMap() { this.maxCapacity = DEFAULT_MAX_CAPACITY; }
public LRULinkedHashMap(int maxCapacity) { super(maxCapacity, DEFAULT_LOAD_FACTOR, true); this.maxCapacity = maxCapacity; }
@Override protected boolean removeEldestEntry(Map.Entry<K, V> eldest) { return size() > maxCapacity; }
@Override public boolean containsKey(Object key) { try { lock.lock(); return super.containsKey(key); } finally { lock.unlock(); } }
@Override public V get(Object key) { try { lock.lock(); return super.get(key); } finally { lock.unlock(); } }
@Override public V put(K key, V value) { try { lock.lock(); return super.put(key, value); } finally { lock.unlock(); } }
@Override public V remove(Object key) { try { lock.lock(); return super.remove(key); } finally { lock.unlock(); } }
@Override public int size() { try { lock.lock(); return super.size(); } finally { lock.unlock(); } }
@Override public void clear() { try { lock.lock(); super.clear(); } finally { lock.unlock(); } }
public int getMaxCapacity() { return maxCapacity; }
public void setMaxCapacity(int maxCapacity) { this.maxCapacity = maxCapacity; }
}
|
测试代码及结果
1 2 3 4 5 6 7 8 9 10 11 12 13 14 15 16 17 18 19 20 21 22 23 24 25 26 27 28 29 30 31 32 33
| package com.ipaynow.tool.lru;
import java.time.LocalDateTime; import java.time.format.DateTimeFormatter; import java.util.Iterator; import java.util.Map;
public class LRUTest {
public static void main(String[] args) throws InterruptedException {
LRULinkedHashMap<String, String> map = new LRULinkedHashMap<>(5);
for (int i = 0; i < 10; i++) { Thread.sleep(1000); map.put(LocalDateTime.now().format(DateTimeFormatter.ofPattern("yyyy-MM-dd HH:mm:ss SSS")), "value" + i); }
for (Iterator<Map.Entry<String, String>> iterator = map.entrySet().iterator(); iterator.hasNext(); ) { Map.Entry<String, String> entry = iterator.next(); String key = entry.getKey(); String value = entry.getValue(); System.out.println(key + "------------" + value); } }
}
|
控制台输出结果:
1 2 3 4 5 6 7
| 2018-11-20 11:13:21 398------------value5 2018-11-20 11:13:22 399------------value6 2018-11-20 11:13:23 400------------value7 2018-11-20 11:13:24 400------------value8 2018-11-20 11:13:25 400------------value9
Process finished with exit code 0
|