go實現LRU cache

來源:互聯網
上載者:User
這是一個建立於 的文章,其中的資訊可能已經有所發展或是發生改變。

1. LRU簡介

1.1 概述

緩衝資源通常比較昂貴,通常資料量較大時,會竟可能從較少的緩衝滿足儘可能多訪問,這裡有一種假設,通常最近被訪問的資料,那麼它就有可能會被後續繼續訪問,基於這種假設,將所有的資料按訪問時間進行排序,並按驅逐出舊資料,那麼存在緩衝的資料就為熱點資料,這樣既節省了記憶體資源,又極大的滿足了訪問.LRU(Least recently used)演算法就是基於這種假設的一直緩衝置換演算法.

1.2 演算法流程

假設緩衝大小為4,而寫入順序為A B C D E D F.訪問順序分為寫入以及讀取兩種操作,寫入需要更新訪問時間,並且當資料到達最大緩衝時需要逐出資料,而讀取只會更新訪問時間,寫入置換演算法流程如所示.

當未到達緩衝大小時,所有資料按寫入儲存,並記錄寫入次序.
寫入E時緩衝已經滿,且E的值不存在,需要逐出最久未訪問的資料A,此時緩衝內容為E D C B.
下一個寫入D, D在緩衝中,直接更新D的訪問次序,此時緩衝內容為 D E C B
下一個寫入F, F不在緩衝中,逐出緩衝中的末尾C,此時緩衝內容為 F D E C

2 go實現

2.1思路

採用go,可以使用list加map實現LRU cache,具體思路為:
寫入時,先從map中查詢,如果能查詢,如果能查詢到值,則將該值的在List中移動到最前面.如果查詢不到值,則判斷當前map是否到達最大值,如果到達最大值則移除List最後面的值,同時刪除map中的值,如果map容量未達最大值,則寫入map,同時將值放在List最前面.

讀取時,從map中查詢,如果能查詢到值,則直接將List中該值移動到最前面,返回查詢結果.

為保證並發安全,需要引入讀寫鎖.
另外,存在讀取List中內容反差map的情況,因為聲明一個容器物件同時儲存key以及value, List中以及map中儲存的都是容器物件的引用.
引入原子物件對命中數以及未命中數等指標進行統計

2.2 關鍵代碼

完整代碼見: https://github.com/g4zhuj/cache

  • Set(寫入操作)
func (c *MemCache) Set(key string, value interface{}) {    c.mutex.Lock()    defer c.mutex.Unlock()    if c.cache == nil {        c.cache = make(map[interface{}]*list.Element)        c.cacheList = list.New()    }    //判斷是否在map中,如果在map中,則將value從list中移動到前面.    if ele, ok := c.cache[key]; ok {        c.cacheList.MoveToFront(ele)        ele.Value.(*entry).value = value        return    }    //如果不再map中,將值存到List最前面    ele := c.cacheList.PushFront(&entry{key: key, value: value})    c.cache[key] = ele    //判斷是否到達容量限制,到達容量限制時刪除List中最後面的值.    if c.maxItemSize != 0 && c.cacheList.Len() > c.maxItemSize {        c.RemoveOldest()    }}
  • Get(讀取操作)
func (c *MemCache) Get(key string) (interface{}, bool) {    c.mutex.RLock()    defer c.mutex.RUnlock()    c.gets.Add(1)    //如果讀取到值,移動在List中位置,並返回value    if ele, hit := c.cache[key]; hit {        c.hits.Add(1)        c.cacheList.MoveToFront(ele)        return ele.Value.(*entry).value, true    }    return nil, false}

3. 參考

https://en.wikipedia.org/wiki...

相關文章

聯繫我們

該頁面正文內容均來源於網絡整理,並不代表阿里雲官方的觀點,該頁面所提到的產品和服務也與阿里云無關,如果該頁面內容對您造成了困擾,歡迎寫郵件給我們,收到郵件我們將在5個工作日內處理。

如果您發現本社區中有涉嫌抄襲的內容,歡迎發送郵件至: info-contact@alibabacloud.com 進行舉報並提供相關證據,工作人員會在 5 個工作天內聯絡您,一經查實,本站將立刻刪除涉嫌侵權內容。

A Free Trial That Lets You Build Big!

Start building with 50+ products and up to 12 months usage for Elastic Compute Service

  • Sales Support

    1 on 1 presale consultation

  • After-Sales Support

    24/7 Technical Support 6 Free Tickets per Quarter Faster Response

  • Alibaba Cloud offers highly flexible support services tailored to meet your exact needs.