leetcode-145-LRU cache
来源:互联网 发布:前端框架 知乎 编辑:程序博客网 时间:2024/06/02 05:10
问题
题目:[leetcode-145]
思路
参考了[O(1) unordered_map + list + splice]
参考者代码的思路非常清晰。
首先,插入和获取的时间复杂度在O(1),不能用deque去实现。否则无法到达常数。采用链表,插入,删除的时间复杂度都是o(1)。需要双向链表,可以自己实现。可以使用stl::list. 由于链表不支持随机访问,所以,做一次哈希。
代码
class LRUCache {public: LRUCache(int capacity) : cap_(capacity) {} int get(int key) { if( cache_map_.find(key) == cache_map_.end() ) return -1; else{ int val = cache_map_[key]->val; cache_list_.splice( cache_list_.begin(), cache_list_, cache_map_[key] ); return val; } } void put(int key, int value) { if( cache_map_.find(key) != cache_map_.end() ){ cache_map_[key]->val = value; cache_list_.splice(cache_list_.begin(), cache_list_, cache_map_[key]); }else{ element e(key, value); if(cache_list_.size() < cap_){ cache_list_.push_front(e); cache_map_[key] = cache_list_.begin(); }else{ cache_map_.erase(cache_list_.back().key); cache_list_.pop_back(); cache_list_.push_front(e); cache_map_[key] = cache_list_.begin(); } } }private: struct element{ int key; int val; element(): key(0),val(0){} element(int k, int v) : key(k), val(v){} }; std::list<element> cache_list_; std::unordered_map< int, std::list<element>::iterator > cache_map_; int cap_;};/** * 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); */
代码1
自己实现了循环双链表,注意pop_back的时候,别忘了从哈希表删除。
class LRUCache {public: LRUCache(int capacity) : cap_(capacity), size_(0) { head_ = tail_ = new Node(); assert(head_); assert(cap_); } int get(int key) { std::cout << "get: " << key << std::endl; if( cache_map_.find(key) == cache_map_.end() ) return -1; else{ CacheList p = cache_map_[key]; move_to_head(p); return p->val; } } void put(int key, int value) { std::cout << "put: " << key << "," << value << std::endl; if( cache_map_.find(key) != cache_map_.end() ){ CacheList p = cache_map_[key]; p->val = value; move_to_head(p); }else{ CacheList p = new Node(); p->key = key; p->val = value; ++size_; if(size_ <= cap_){ insert_head(p); cache_map_[key] = p; }else{ size_ = cap_; cache_map_.erase(tail_->key); delete_tail(); insert_head(p); cache_map_[key] = p; } } } ~LRUCache() { delete head_; }private: struct Node { int key; int val; Node* next; Node* prev; Node() { memset(this, 0, sizeof(Node));} }; typedef Node* CacheList; CacheList head_; CacheList tail_; int cap_; int size_; unordered_map<int, CacheList> cache_map_;private: void move_to_head(CacheList p){ if( head_ == tail_ ) return ; if( head_->next == p ) return ; else{ if(p == tail_){ tail_ = tail_->prev; tail_->next = NULL; } else{ CacheList pre = p->prev; CacheList nex = p->next; pre->next = nex; nex->prev = pre; } insert_head(p); } } void insert_head(CacheList p){ CacheList q = head_->next; p->next = q; p->prev = head_; head_->next = p; if(q) q->prev = p; else tail_ = p; } void delete_tail(){ if(head_ == tail_) return; CacheList p = tail_; tail_ = tail_->prev; tail_->next = NULL; delete p; }};
代码2
bug在于,要区别两类迭代器。不是一回事!
class LRUCache {public: LRUCache(int capacity) { cap_ = capacity; } int get(int key) { if( cache_map_.find(key) == cache_map_.end() ) return -1; else{ Iter it = cache_map_[key]; // move to head cache_list_.splice( cache_list_.begin(), cache_list_, it ); // return value return it->second; } } void put(int key, int value) { if( cache_map_.find(key) != cache_map_.end() ){ Iter it = cache_map_[key]; // update the value it->second = value; // move to head cache_list_.splice( cache_list_.begin(), cache_list_, it ); } else{ if( cache_list_.size() == cap_ ){ cache_map_.erase( cache_list_.back().first ); cache_list_.pop_back(); } Node node(key, value); cache_list_.push_front(node); cache_map_[key] = cache_list_.begin(); } }private: typedef pair<int, int> Node; typedef list<Node>::iterator Iter; list<Node> cache_list_; unordered_map<int, Iter> cache_map_; int cap_;};
阅读全文
0 0
- leetcode 145: LRU Cache
- leetcode-145-LRU cache
- LeetCode LRU 缓存 LRU Cache
- LRU Cache | leetcode
- Leetcode: LRU Cache
- LeetCode:LRU Cache
- Leetcode: LRU Cache
- [LeetCode] LRU Cache
- leetcode之LRU Cache
- [LeetCode]LRU Cache
- [LeetCode] LRU Cache
- leetcode LRU Cache
- LeetCode题解:LRU Cache
- LeetCode | LRU Cache
- Leetcode: LRU Cache
- [LeetCode] LRU Cache
- LeetCode OJ:LRU Cache
- Leetcode LRU Cache
- [LeetCode] 107. Binary Tree Level Order Traversal II
- 移动端rem布局
- Shufflenet论文阅读笔记
- ubuntu 16.04 C++ 调用python脚本实现方式
- CSS盒模型
- leetcode-145-LRU cache
- 通过超链接进入到另一个页面执行js
- Linux下命令行音乐播放器
- java中分布式架构的演变和介绍
- jquery 控制下拉列表
- Codeforces Round #430 (Div. 2) 总结
- 韩信点兵算法
- Python初学——窗口视窗Tkinter
- Ubuntu 中apt update和upgrade 的区别