今天写这道题,背过八股文的都应该知道LRU算法缓存的基本原理,在 Java
语言中,同样有类似的数据结构 LinkedHashMap,
本题我们采用自己创建哈希表+双链表的形式简单实现一下
对于get操作:通过cache.get(key)获取,如果不存在则直接返回-1,否则返回对于key的value并把该结点移动到链表头部
对于put操作:通过cache.get(key)获取,如果存在则直接替换该结点的value并把该结点移动到链表头部,否则创建新的结点,把它put到chache中,然后添加到链表头部并且size++,最后判断size是否大于capacity,如果大于则需要移除链表尾部结点,并且需要移除cache中对应的结点,最后size--
代码如下
class LRUCache {// 双链表class DLinkedNode {int key;int value;DLinkedNode prev;DLinkedNode next;public DLinkedNode() {}public DLinkedNode(int _key, int _value) {key = _key;value = _value;}}// 创建哈希表private Map<Integer, DLinkedNode> cache = new HashMap<>();// 哈希表当前结点个数private int size;// 最大结点个数,不能超过此阈值,否则需要进行移除链表尾结点操作private int capacity;// 双链表伪头部和伪尾部DLinkedNode head, tail;// 传入一个int型数字构建一个LRUCache对象public LRUCache(int capacity) {this.size = 0;this.capacity = capacity;head = new DLinkedNode();tail = new DLinkedNode();head.next = tail;tail.prev = head;}// get操作public int get(int key) {DLinkedNode node = cache.get(key);if (node == null) {return -1;}moveToHead(node);return node.value;}public void moveToHead(DLinkedNode node) {removeNode(node);addToHead(node);}public void removeNode(DLinkedNode node) {node.next.prev = node.prev;node.prev.next = node.next;}public void addToHead(DLinkedNode node) {node.prev = head;node.next = head.next;head.next.prev = node;head.next = node;}// put操作public void put(int key, int value) {DLinkedNode node = cache.get(key);if (node == null) {DLinkedNode newNode = new DLinkedNode(key, value);cache.put(key, newNode);addToHead(newNode);size++;if (size > capacity) {DLinkedNode tail = removeTail();cache.remove(tail.key);size--;}} else {node.value = value;moveToHead(node);}}private DLinkedNode removeTail() {DLinkedNode res = tail.prev;removeNode(res);return res;}
}
题目链接:题单 - 力扣(LeetCode)全球极客挚爱的技术成长平台