LRU算法实现
2016-10-22 14:25
211 查看
LRU
LRU(Least recently used,最近最少使用)算法根据数据的历史访问记录来进行淘汰数据,其核心思想是“如果数据最近被访问过,那么将来被访问的几率也更高”。
最常见的实现是使用一个链表保存缓存数据,详细算法实现如下:
新数据插入到链表头部;
每当缓存命中(即缓存数据被访问),则将数据移到链表头部;
当链表满的时候,将链表尾部的数据丢弃。
【命中率】
当存在热点数据时,LRU的效率很好,但偶发性的、周期性的批量操作会导致LRU命中率急剧下降,缓存污染情况比较严重。
【复杂度】
实现简单。
【代价】
命中时需要遍历链表,找到命中的数据块索引,然后需要将数据移到头部。
这是go利用container/list实现版本,出自Brad Fitzpatrick之手
Cache对象是内存中的一个容器,用来存放查询的结果。我们将Cache对象实现为一个List。另外,为了提升访问效率,用一个map结构来索引key及其对应的值。
LRU(Least recently used,最近最少使用)算法根据数据的历史访问记录来进行淘汰数据,其核心思想是“如果数据最近被访问过,那么将来被访问的几率也更高”。
最常见的实现是使用一个链表保存缓存数据,详细算法实现如下:
新数据插入到链表头部;
每当缓存命中(即缓存数据被访问),则将数据移到链表头部;
当链表满的时候,将链表尾部的数据丢弃。
【命中率】
当存在热点数据时,LRU的效率很好,但偶发性的、周期性的批量操作会导致LRU命中率急剧下降,缓存污染情况比较严重。
【复杂度】
实现简单。
【代价】
命中时需要遍历链表,找到命中的数据块索引,然后需要将数据移到头部。
这是go利用container/list实现版本,出自Brad Fitzpatrick之手
Cache对象是内存中的一个容器,用来存放查询的结果。我们将Cache对象实现为一个List。另外,为了提升访问效率,用一个map结构来索引key及其对应的值。
// Cache is an LRU cache. It is not safe for concurrent access. type Cache struct { // MaxEntries is the maximum number of cache entries before // an item is evicted. Zero means no limit. MaxEntries int // OnEvicted optionally specificies a callback function to be // executed when an entry is purged from the cache. OnEvicted func(key Key, value interface{}) // type List struct { // root Element // sentinel list element, only &root, root.prev, and root.next are used // len int // current list length excluding (this) sentinel element // } // type Element struct { // // Next and previous pointers in the doubly-linked list of elements. // // To simplify the implementation, internally a list l is implemented // // as a ring, such that &l.root is both the next element of the last // // list element (l.Back()) and the previous element of the first list // // element (l.Front()). // next, prev *Element // // The list to which this element belongs. // list *List // // The value stored with this element. // Value interface{} // } ll *list.List cache map[interface{}]*list.Element } // A Key may be any value that is comparable. See http://golang.org/ref/spec#Comparison_operators type Key interface{} //在list中存放的是entry type entry struct { key Key value interface{} } // New creates a new Cache. // If maxEntries is zero, the cache has no limit and it's assumed // that eviction is done by the caller. func New(maxEntries int) *Cache { return &Cache{ MaxEntries: maxEntries, ll: list.New(), cache: make(map[interface{}]*list.Element), } } // Add adds a value to the cache. func (c *Cache) Add(key Key, value interface{}) { if c.cache == nil { c.cache = make(map[interface{}]*list.Element) c.ll = list.New() } if ee, ok := c.cache[key]; ok { c.ll.MoveToFront(ee) ee.Value.(*entry).value = value return } //返回Element作为map的value ele := c.ll.PushFront(&entry{key, value}) c.cache[key] = ele if c.MaxEntries != 0 && c.ll.Len() > c.MaxEntries { //执行清理 c.RemoveOldest() } } // Get looks up a key's value from the cache. func (c *Cache) Get(key Key) (value interface{}, ok bool) { if c.cache == nil { return } if ele, hit := c.cache[key]; hit { c.ll.MoveToFront(ele) return ele.Value.(*entry).value, true } return } // Remove removes the provided key from the cache. func (c *Cache) Remove(key Key) { if c.cache == nil { return } if ele, hit := c.cache[key]; hit { c.removeElement(ele) } } // RemoveOldest removes the oldest item from the cache. func (c *Cache) RemoveOldest() { if c.cache == nil { return } ele := c.ll.Back() if ele != nil { c.removeElement(ele) } } func (c *Cache) removeElement(e *list.Element) { c.ll.Remove(e) kv := e.Value.(*entry) delete(c.cache, kv.key) if c.OnEvicted != nil { c.OnEvicted(kv.key, kv.value) } } // Len returns the number of items in the cache. func (c *Cache) Len() int { if c.cache == nil { return 0 } return c.ll.Len() }
相关文章推荐
- LRU算法实现(draft2)
- 蛙蛙推荐: LRU缓存的实现算法讨论
- LRU算法的实现
- LRU算法实现
- 基于LRU算法的连接检测实现
- FIFO与LRU 算法实现(java)
- leetcode LRU Cache(高级缓存的最近最少使用算法实现)
- 简单LRU算法实现缓存
- LRU算法的简单实现( C语言 + uthash包)
- 用LinkedHashMap实现LRU算法
- 蛙蛙推荐: LRU缓存的实现算法讨论
- 简单LRU算法实现的Cache(C++)
- LRU算法之实现
- LRU缓存的实现算法讨论
- 利用LinkedHashMap实现LRU算法缓存
- LRU算法的实现
- 经典操作系统教材中的LRU算法的自编c++实现及源码。
- 简单LRU算法实现缓存
- 基于LRU算法的缓存实现
- [Leetcode] LRU 算法实现