标签:缓存 大小 删除 get cap find 节点 获取 哈希
题目:
解答:
1 // 总的思想就是 哈希双向链表 2 struct Node 3 { 4 int key; 5 int value; 6 Node* pre; 7 Node* next; 8 // 构造函数初始化 9 Node(int key, int value) : key(key), value(value), pre(nullptr), next(nullptr){} 10 }; 11 12 class LRUCache { 13 private: 14 int size;// 缓冲区大小 15 Node* head; 16 Node* tail; 17 map<int, Node*> p; 18 19 public: 20 LRUCache(int capacity) 21 { 22 this->size = capacity; 23 head = nullptr; 24 tail = nullptr; 25 } 26 27 // 获取缓冲区中 key 对应的 value 28 int get(int key) 29 { 30 // 1.当该 key 值存在 31 if(p.count(key) > 0) 32 { 33 // 删除该 key 对应的原来节点 34 Node* cur = p[key]; 35 int value = cur->value; 36 37 remove(cur); // 这里仅仅删除哈希双向链表中的节点,不必删除哈希表中的 38 39 // 将节点重现插入到缓冲区的头部 40 setHead(cur); 41 return value; 42 } 43 // 2.当该 key 值不存在 44 return -1; 45 } 46 47 // 将key-value值存入缓冲区 48 void put(int key, int value) 49 { 50 // 1.当该 key 值存在 51 if(p.count(key) > 0) 52 { 53 // 删除该 key 对应的原来节点 54 Node* cur = p[key]; 55 cur->value = value; 56 57 remove(cur); // 这里仅仅删除哈希双向链表中的节点,不必删除哈希表中的 58 59 // 将节点重现插入到缓冲区的头部 60 setHead(cur); 61 } 62 else// 2.当该 key 值不存在 63 { 64 Node* node = new Node(key, value); 65 // 判断当前缓冲区大小已经满了 66 if(p.size() >= size) 67 { 68 // 删除尾部节点 69 map<int, Node*>::iterator it = p.find(tail->key);// 返回迭代器类型 70 remove(tail); 71 p.erase(it);// 这里erase 函数参数是迭代器类型,所以上面需要使用迭代器类型 72 // 将新节点插入到缓冲区的头部 73 } 74 //else 此时因为动作和上面重复,所以直接合并使用 75 //还没有满:将新节点插入到缓冲区的头部 76 { 77 setHead(node); 78 p[key] = node; 79 } 80 } 81 } 82 83 // 删除当前节点 84 void remove(Node* cur) 85 { 86 // 当前节点是 head 87 if(cur == head) 88 head = cur->next; 89 else if(cur == tail)// 当前节点是 tail 90 tail = cur->pre; 91 else// 当前节点是一般节点 92 { 93 cur->pre->next = cur->next; 94 cur->next->pre = cur->pre; 95 } 96 } 97 // 将当前节点插入到头部 98 void setHead(Node* cur) 99 { 100 cur->next = head; 101 if(head != nullptr) 102 { 103 head->pre = cur; 104 } 105 head = cur;//重现更新head 106 107 if(tail==nullptr) 108 { 109 tail = head; 110 } 111 } 112 };
标签:缓存 大小 删除 get cap find 节点 获取 哈希
原文地址:https://www.cnblogs.com/ocpc/p/12832915.html