单位自己写的LruMap有内存泄露的问题.
自己尝试用JDK自带的结构实现一个.
功能
1.可以设置上线,一旦到达上线,根据LRU删除数据
2.可以设置过期时间.到期自动删除.
-
import java.text.SimpleDateFormat;
-
import java.util.Calendar;
-
import java.util.Date;
-
import java.util.LinkedHashMap;
-
import java.util.concurrent.DelayQueue;
-
import java.util.concurrent.Delayed;
-
import java.util.concurrent.TimeUnit;
-
import java.util.concurrent.locks.ReadWriteLock;
-
import java.util.concurrent.locks.ReentrantReadWriteLock;
-
-
public class LruMap<K, V> {
-
private final LinkedHashMap<K, V> map;
-
private final int capacity;
-
private final DelayQueue<Node<K>> dq;
-
private final ReadWriteLock lock = new ReentrantReadWriteLock();
-
-
public LruMap(int capacity) {
-
this.capacity = capacity;
-
dq = new DelayQueue<Node<K>>();
-
map = new LinkedHashMap<>(capacity, 0.75f, true);
-
Thread thread = new Thread(new Runnable() {
-
-
@Override
-
public void run() {
-
while (true) {
-
try {
-
Node<K> node = dq.take();
-
lock.writeLock().lock();
-
map.remove(node.get());
-
lock.writeLock().unlock();
-
-
System.out.println("过期删除:" + node);
-
print();
-
} catch (InterruptedException e) {
-
e.printStackTrace();
-
}
-
-
}
-
}
-
});
-
-
thread.setDaemon(true);
-
thread.start();
-
}
-
-
private void print(){
-
System.out.println("================");
-
for(K k : map.keySet()){
-
System.out.print(k+",");
-
}
-
System.out.print("\n");
-
}
-
-
public V get(K k) {
-
lock.readLock().lock();
-
V v = map.get(k);
-
lock.readLock().unlock();
-
print();
-
return v;
-
}
-
-
public void set(K k, V v) {
-
lock.writeLock().lock();
-
if (map.size() == this.capacity) {
-
remove();
-
}
-
map.put(k, v);
-
lock.writeLock().unlock();
-
print();
-
}
-
-
public void set(K k, V v, long timeout, TimeUnit unit) {
-
Node<K> node = new Node<K>(k, timeout, unit);
-
lock.writeLock().lock();
-
if (map.size() == this.capacity) {
-
remove();
-
}
-
map.put(k, v);
-
dq.offer(node);
-
lock.writeLock().unlock();
-
print();
-
}
-
-
private void remove() {
-
K k = map.keySet().iterator().next();
-
map.remove(k);
-
System.out.println("LRU删除:" + k);
-
}
-
-
public static void main(String[] args) throws InterruptedException {
-
LruMap<Integer, Integer> map = new LruMap<>(3);
-
-
map.set(1, 1);
-
map.set(2, 2);
-
map.set(3, 3);
-
-
map.set(4, 4);
-
-
map.get(2);
-
map.set(5, 5);
-
-
-
map.set(5, 5, 5, TimeUnit.SECONDS);
-
map.set(10, 10, 10, TimeUnit.SECONDS);
-
Thread.currentThread().join();
-
}
-
}
-
-
class Node<K> implements Delayed {
-
private long timeout;
-
private long createtime;
-
private K k;
-
-
public Node(K k, long timeout, TimeUnit unit) {
-
this.k = k;
-
this.timeout = unit.toNanos(timeout);
-
this.createtime = System.nanoTime();
-
}
-
-
public K get() {
-
return k;
-
}
-
-
private long now() {
-
return System.nanoTime();
-
}
-
-
@Override
-
public String toString() {
-
return "Key:" + this.k + ",timeout:" + TimeUnit.SECONDS.convert(timeout, TimeUnit.NANOSECONDS) + "秒";
-
}
-
-
@Override
-
public int compareTo(Delayed o) {
-
Long l1 = Long.valueOf(this.getDelay(TimeUnit.NANOSECONDS));
-
Long l2 = Long.valueOf(o.getDelay(TimeUnit.NANOSECONDS));
-
return l1.compareTo(l2);
-
}
-
-
@Override
-
public long getDelay(TimeUnit unit) {
-
return unit.convert(createtime + timeout - now(), TimeUnit.NANOSECONDS);
-
}
-
}
来自 “ ITPUB博客 ” ,链接:https://blog.itpub.net/29254281/viewspace-2127204/
,如需转载,请注明出处,否则将追究法律责任。