2023字节面试题——实现能定期回收旧条目的LRU缓存
这个手撕的原题是leetcode的LRU,主要是对std::chrono的使用,在原题LRU的基础上多加一个函数定期执行,然后一把大锁实现互斥访问。
C++参考代码如下:
#include <iostream> #include <thread> #include <chrono> #include <vector> #include <mutex> #include <unordered_map> #include <string> #define time_point std::chrono::system_clock::time_point #define now() std::chrono::system_clock::now() struct Node { int key, value; time_point time; Node *prev, *next; Node(){} Node(int k, int v){key = k; value = v; prev = nullptr; next = nullptr;} }; class Cache { private: Node *head, *tail; int size = 0, capacity = 0; std::unordered_map<int, Node*> map; std::mutex mutex; int timegap = 0; int scangap = 0; public: Cache (int capacity, int tg, int sg) { this->capacity = capacity; timegap = tg; scangap = sg; head = new Node(); tail = new Node(); head->prev = nullptr; tail->next = nullptr; head->next = tail; tail->prev = head; } int getScangap() { return this->scangap; } int put(int key, int value) { mutex.lock(); if (map.find(key) == map.end()) { Node *node = new Node(); node->key = key; node->value = value; map[key] = node; if (size == capacity) { Node *last = tail->prev; last->prev->next = tail; tail->prev = last->prev; map.erase(last->key); delete last; } else { size++; } head->next->prev = node; node->next = head->next; head->next = node; node->prev = head; node->time = now(); } else { Node *node = map[key]; node->value = value; if (node == head->next) { mutex.unlock(); return 1; } node->prev->next = node->next; node->next->prev = node->prev; node->prev = nullptr; node->next = nullptr; head->next->prev = node; node->next = head->next; node->prev = head; head->next = node; node->time = now(); } mutex.unlock(); return 1; } int get(int key) { mutex.lock(); if (map.find(key) == map.end()) { mutex.unlock(); return -1; } Node *node = map[key]; node->prev->next = node->next; node->next->prev = node->prev; node->prev = nullptr; node->next = nullptr; node->next = head->next; head->next->prev = node; node->prev = head; head->next = node; int res = node->value; node->time = now(); mutex.unlock(); return res; } int clear() { mutex.lock(); Node *node = head->next; while (node != tail) { time_point timenow = now(); if (std::chrono::duration_cast<std::chrono::milliseconds>(timenow - node->time).count() > timegap) { node->prev->next = node->next; node->next->prev = node->prev; map.erase(node->key); delete node; } node = node->next; } mutex.unlock(); return 0; } }; int main() { Cache cache{5, 5000, 5000}; std::thread job1([&cache](){ while(true) { cache.clear(); std::this_thread::sleep_for(std::chrono::milliseconds(cache.getScangap())); } }); std::thread job2([&cache](){ while (true) { std::string cmd; int key, value; std::cin>>cmd; if (cmd == "get") { std::cin>>key; std::cout<<cache.get(key)<<'\n'; } else { std::cin>>key>>value; std::cout<<cache.put(key, value)<<'\n'; } } }); job1.join(); job2.join(); return 0; }

浙公网安备 33010602011771号