package com.bruce.homework0402.lru; /** * 用双向链表实现LRU算法 * */ public class LRUPageFrame { private int capacity;//页容量 private Node first;// 链表头 private Node last;// 链表尾 private int size = 0;//缓存的页面数量 public LRUPageFrame(int capacity) { this.capacity = capacity; } /** * 获取缓存中对象 * * @param */ public void access(int pageNum) { //第一次存放 if (size == 0) { Node node = new Node(pageNum); node.next = null; node.prev = null; this.first = this.last = node; size++; } else if (size == 1 && size < capacity) { addToFirst(pageNum); } else { if (first != null && first.pageNum == pageNum) {//目标页已经存放在first节点 ,不做操作 return; } if (last != null && last.pageNum == pageNum) {//目标页已经存放在last节点 ,将该节点放到第一个 moveLastToFirst(); return; } //目标页不在第一个和最后一个节点,从第一个节点往后查找 Node node = first; while (node.next != null) { node = node.next; if (node.pageNum == pageNum) { break; } } if (node == last) { addToFirst(pageNum); if (size > capacity) {//添加新节点后,size大于capacity,把最后一个节点去掉,last 指针向前移动一位 last = last.prev; last.next = null; } } else { moveToFirst(node); } } } private Node exist(int pageNum) { Node node = first; while(node != null) { if (node.pageNum == pageNum) { return node; } node = node.next; } return null; } private static class Node { Node prev; Node next; int pageNum; Node() {} Node(int pageNum) { this.pageNum = pageNum; } } private void moveLastToFirst() { //将first和last双向链接起来 last.next = first; first.prev = last; //移动first和last的“指针” first = last; last = last.prev; //打断first和last的双向链接 last.next = null; first.prev = null; } private void addToFirst(int pageNum) { Node node = new Node(pageNum); node.next = first; node.prev = null; first.prev = node; first = node; size++; } private void moveToFirst(Node node) { node.prev.next = node.next; node.next.prev = node.prev; node.next = first; node.prev = null; first.prev = node; first = node; } public String toString(){ StringBuilder buffer = new StringBuilder(); Node node = first; while(node != null){ buffer.append(node.pageNum); node = node.next; if(node != null){ buffer.append(","); } } return buffer.toString(); } }