Leetcode 146. LRU Cache
2018-02-07 21:57
417 查看
Leetcode 146. LRU Cache
前言
今天电话面试,具体哪一家公司就不透露了。面试官叫我实现一个Cache。
我个人感觉答得不好,一开始就跑偏了。
事后发现这是一道经典题,有多经典呢?
经典到我队友昨天也说他面试另一家公司也出了这道题,然而我理解错了他的意思,导致没细看。
经典到我一和学长说,考Cache,学长就知道是这道题。(学长还是强)
经典到一位网友说
遇到过,很正常; 没遇到,早晚会遇到。 (出处)
由于我一开始就跑偏了,数据结构选错了,现在想想,面试官很多提醒我的点都是这题的注意事项,然而当时并不知道。
挫折在所难免,关键是不能在同一个地方跌倒两次。
题目
题目连接首先弄清楚LRU是什么?
参考连接
最久没有访问的内容作为替换对象。
总结一下:
这个Cache有一个容量,在构造函数中会给出。
然后往里面put,如果容量没有满,就直接put。
否则呢,就开始替换。
怎么替换呢?
最久没有访问的作为替换对象。
get函数,输入key
如果命中了,就返回value
否则就返回-1.
最好O(1)实现。
那我们先不考虑LRU。直接就是一个Cache。既然要O(1),就用unordered_map就好了。
可以写出出这段代码
int get(int key) { if (mp.count(key)) { return mp[key]; } else { return -1; } } void put(int key, int value) { mp[key] = value; }
然后实现LRU,最久没有访问的出去。
既然要O(1),所有全网的解法都是拿list来说实现的。
set(key, value)时
首先看key在不在map里面,如果在就放在最前面,修改就好了,也不需加到Cache里去了。
当cache没有满的时候,一次加到list最前面。
当cache满的时候,就把最后一个拿掉。
get(key)的时候,就把
把list里面key为这个元素给放到最前面。
这样都是O(1)的。
这样我们需要同时记录每个key在list中的位置,即迭代器。
把这些功能加进去,就会形成正确代码。
我们发现可以复用一个函数,就叫它hit吧。
完整代码(带测试)
#include <bits/stdc++.h> using namespace std; class LRUCache { private: unordered_map<int, pair<int, list<int>::iterator> > mp; int capacity; int sz; list<int> li; void hit(int key) { auto it = mp[key].second; li.erase(it); li.push_front(key); mp[key].second = li.begin(); } public: LRUCache(int capacity) : capacity(capacity) { sz = 0; } int get(int key) { if (mp.count(key)) { hit(key); return mp[key].first; } else { return -1; } } void put(int key, int value) { if (mp.count(key)) { mp[key].first = value; hit(key); return; } if (sz == capacity) { mp.erase(li.back()); li.pop_back(); } else { sz++; } li.push_front(key); mp[key].first = value; mp[key].second = li.begin(); } }; /** * Your LRUCache object will be instantiated and called as such: * LRUCache obj = new LRUCache(capacity); * int param_1 = obj.get(key); * obj.put(key,value); */ int main() { LRUCache cache = LRUCache(2); cache.put(1, 1); cache.put(2, 2); cout << cache.get(1) << endl; // returns 1 cache.put(3, 3); // evicts key 2 cout << cache.get(2) << endl; // returns -1 (not found) cache.put(4, 4); // evicts key 1 cout << cache.get(1) & 9611 lt;< endl; // returns -1 (not found) cout << cache.get(3) << endl; // returns 3 cout << cache.get(4) << endl; // returns 4 }
这道题的难点就在于概念不清楚,需要查资料。对于没有接触过的人来说,可以确实配得上leetcode的hard难度。
相关文章推荐
- leetcode No146. LRU Cache
- leetcode 146. LRU Cache
- [LeetCode] 146. LRU Cache
- [leetcode] 146. LRU Cache
- leetcode 146. LRU Cache
- [leetcode] 146. LRU Cache
- LeetCode 146. LRU Cache
- [LeetCode]146. LRU Cache
- LeetCode 之 LRU Cache Java实现
- 146. LRU Cache
- Leetcode LRU Cache
- leetcode LRU cache
- #leetcode#LRU Cache
- LeetCode LRU Cache
- [leetcode]LRU Cache @ Python
- leetcode_Design and implement a data structure for Least Recently Used (LRU) cache
- LeetCode146:LRU Cache
- Leetcode LRU Cache
- leetcode LRU Cache
- LeetCode LRU Cache