Design and implement a data structure for cache. It should support the following operations: get
and put
.
get(key)
- Get the value (will always be positive) of the key if the key exists in the cache, otherwise return -1.
put(key, value)
- Set or insert the value if the key is not already present. When the cache reaches its capacity, it should invalidate the least frequently used item before inserting a new item. For the purpose of this problem, when there is a tie (i.e., two or more keys that have the same frequency), the least recently used key would be evicted. Follow up:
Could you do both operations in O(1) time complexity?Example:
LFUCache cache = new LFUCache( 2 /* capacity */ );cache.put(1, 1);cache.put(2, 2);cache.get(1); // returns 1cache.put(3, 3); // evicts key 2cache.get(2); // returns -1 (not found)cache.get(3); // returns 3.cache.put(4, 4); // evicts key 1.cache.get(1); // returns -1 (not found)cache.get(3); // returns 3cache.get(4); // returns 4
解题思路:
I use two structure to solve this problem
list<pair<int, list<int>>> records the visit info(count & time) of each key, let's call it big-L
the most inner <int> is the key, and list<int> rank them according to visit-time, from old to new.pair<int, list<int>> associate each list<int> with visit-counte.g. {2, {a, b}} means both a & b has been visited for 2 times, but b has a newer last-visit-timeand the other structure unordered_map<int, info> keeps the value and iterators in big-L of each key
so everytime we have to remove one element, we remove the first <int> of first pair<int, list<int>> in big-L
and everytime we have to insert one element, just check if the first pair's count equals 1. If it is, use that pair, push new element to its back; otherwise, insert a new pair.
and everytime an element is visited, we move it from the old pair to the next one in big-L. if no following pair exists, or following pair's count is not old-count+1, just insert a new pair with old-count+1. don't forget to update the iterators in map :D
横向一个频率(从小到大)链表,纵向一个LRU(从旧到新),
class LFUCache {public: struct info{ int val; list