Design and implement a data structure for Least Frequently Used (LFU) 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 1 cache.put(3, 3); // evicts key 2 cache.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 3 cache.get(4); // returns 4
- #include#include#include#include#include#include#include#include#include#include#include using namespace std;
- typedef pair > PIIT;
- typedef list LPIIT;
- typedef list LPLIST;
- class LFUCache {
- public: LFUCache(int capacity) : _capacity(capacity),
- len(0) {}
- int get(int key, int value = -1) {
- if (_capacity == 0) return - 1;
- auto resf = mpKeyIt.find(key);
- if (resf != mpKeyIt.end()) {
- if (value != -1) resf - >second - >second.first = value;
- auto res = resf - >second - >second.first;
- update(resf - >second);
- return res;
- } else {
- return - 1;
- }
- }
- void put(int key, int value) {
- { // if exist if(_capacity == 0)return; if(get(key, value) != -1) return; } // non-exist if (len >= _capacity) { // delete auto itL0 = mlis.begin(); auto itL1 = itL0->end(); itL1--; auto keyOld = itL1->first; auto frOld = itL1->second.second; mpKeyIt.erase(keyOld); itL1 = itL0->erase(itL1); if (itL0->empty()) { itL0 = mlis.erase(itL0); mpFrIt.erase(frOld); } } else { len++; } auto refs = mpFrIt.find(1); PIIT piit(key, pair(value, 1)); if (refs != mpFrIt.end()) { mpFrIt[1]->push_front(piit); } else { LPIIT lpiit; lpiit.push_front(piit); mlis.push_front(lpiit); mpFrIt[1] = mlis.begin(); } mpKeyIt[key] = mpFrIt[1]->begin(); }private: int _capacity; int len; LPLIST mlis; unordered_map mpFrIt; unordered_map mpKeyIt; void update(LPIIT::iterator it) { // delete old auto fr = it->second.second; auto val = it->second.first; auto key = it->first; auto newFr = fr+1; PIIT piit(key, pair(val, newFr)); it = mpFrIt[fr]->erase(it); auto resf = mpFrIt.find(newFr); if (resf != mpFrIt.end()) { resf->second->push_front(piit); mpKeyIt[key] = resf->second->begin(); } else { auto itp = mpFrIt[fr]; itp++; LPIIT lpiit; lpiit.push_front(piit); itp = mlis.insert(itp, lpiit); mpFrIt[newFr] = itp; mpKeyIt[key] = itp->begin(); } // delete fr if (mpFrIt[fr]->empty()) { mpFrIt[fr] = mlis.erase(mpFrIt[fr]); // delete mlis mpFrIt.erase(fr); // delete mpFrIt } }};
就爱阅读 www.92to.com 网友整理上传, 为您提供最全的知识大全, 期待您的分享,转载请注明出处。
来源: http://www.92to.com/bangong/2017/04-22/20698359.html