Leetcode 146. LRU Cache (Hard) (cpp)
Tag: Desgin
Difficulty: Hard
/*
146. LRU Cache (Hard)
Design and implement a data structure for Least Recently Used (LRU) cache. It should support the following operations: get and set.
get(key) - Get the value (will always be positive) of the key if the key exists in the cache, otherwise return -1.
set(key, value) - Set or insert the value if the key is not already present. When the cache reached its capacity, it should invalidate the least recently used item before inserting a new item.
*/
class KeyValue {
public:
int key, value;
KeyValue *next;
KeyValue (int key, int value) {
next = NULL;
this->key = key;
this->value = value;
}
KeyValue() {
this->next = NULL;
this->key = 0;
this->value = 0;
}
};
class LRUCache{
public:
unordered_map<int, KeyValue*> mapping;
KeyValue *head, *tail;
int capacity, size;
LRUCache(int capacity) {
this->head = new KeyValue(0, 0);
this->tail = head;
this->capacity = capacity;
this->size = 0;
mapping.clear();
}
int get(int key) {
if (mapping.find(key) == mapping.end()) {
return -1;
}
moveToTail(mapping[key]);
return mapping[key]->next->value;
}
void set(int key, int value) {
if (mapping.find(key) != mapping.end()) {
mapping[key]->next->value = value;
moveToTail(mapping[key]);
} else {
KeyValue *node = new KeyValue(key, value);
tail->next = node;
mapping[key] = tail;
tail = node;
size++;
if (size > capacity) {
mapping.erase(head->next->key);
head->next = head->next->next;
if (head->next != NULL) {
mapping[head->next->key] = head;
}
size--;
}
}
}
private:
void moveToTail(KeyValue *prev) {
if (prev->next == tail) {
return;
}
KeyValue *node = prev->next;
prev->next = node->next;
if (node->next != NULL) {
mapping[node->next->key] = prev;
}
tail->next = node;
node->next = NULL;
mapping[node->key] = tail;
tail = node;
}
};