LRUCache.java 3.48 KB
package com.zhaoonline.coupen.cache;

import java.util.HashSet;
import java.util.Iterator;
import java.util.Set;
import java.util.concurrent.ConcurrentHashMap;

/**
 * Created by ZhaoOnline<br/>
 * User: yangyoupeng<br/>
 * Date: 2016/12/15<br/>
 * Time: 17:54<br/>
 * Description:
 */
public class LRUCache<T> {
    private ConcurrentHashMap<String, T> caches = null;

    private CacheEntry<T> first;
    private CacheEntry<T> last;
    private int capacity = 0;

    public LRUCache() {
        this(200);
    }
    public LRUCache(int capacity) {
        this.capacity=capacity;
        this.caches = new ConcurrentHashMap<String,T>(capacity);
    }


    public synchronized T put(String key, T value) {
        CacheEntry<T> entry = getEntry(key);
        if (entry == null) {
            if (caches.size() >= capacity) {
                caches.remove(last.key);
                removeLast();
            }
            entry = new CacheEntry<T>();
            entry.key = key;
        }else{
            entry.value=null;
        }
        entry.value = value;
        moveToFirst(entry);
        return caches.put(key, value);
    }

    public int getSize() {
        return caches.size();
    }

    public synchronized T get(String key) {
        CacheEntry<T> entry = getEntry(key);
        if (entry == null){
            return null;
        }
        moveToFirst(entry);
        return entry.value;
    }


    public synchronized void remove(String key) {
        CacheEntry<T> entry = getEntry(key);
        if (entry != null) {
            if (entry.pre != null)
                entry.pre.next = entry.next;
            if (entry.next != null)
                entry.next.pre = entry.pre;
            if (entry == first)
                first = entry.next;
            if (entry == last)
                last = entry.pre;
        }
        caches.remove(key);
    }

    private void removeLast() {
        if (last != null) {
            last = last.pre;
            if (last == null)
                first = null;
            else
                last.next = null;
        }
    }

    private void moveToFirst(CacheEntry<T> entry) {
        if (entry == first)
            return;
        if (entry.pre != null)
            entry.pre.next = entry.next;
        if (entry.next != null)
            entry.next.pre = entry.pre;
        if (entry == last)
            last = last.pre;
        if (first == null || last == null) {
            first = last = entry;
            return;
        }
        entry.next = first;
        first.pre = entry;
        first = entry;
        entry.pre = null;
    }


    private CacheEntry<T> getEntry(String key) {
        T item = caches.get(key);
        if (item == null) {
            return null;
        }
        CacheEntry<T> entry = new CacheEntry<T>();
        entry.key = key;
        entry.value = item;
        return entry;
    }



    @Override
    public String toString() {
        StringBuilder sb = new StringBuilder();
        CacheEntry<T> entry = first;
        while (entry != null) {
            sb.append(String.format("%s:%s ", entry.key, entry.value));
            entry = entry.next;
        }
        return sb.toString();
    }



    public Set<String> keySet(){
        Set<String> keSet=new HashSet<String>();
        ConcurrentHashMap.KeySetView<String, T> keysSetView= caches.keySet();
        Iterator<String> iter=keysSetView.iterator();
        while(iter.hasNext()){
            String key=iter.next();
            keSet.add(key);
        }
        return keSet;
    }
}