LRU (近期最少使用)演算法 c++實現

來源:互聯網
上載者:User

標籤:依次   根據   需要   移動   erase   iostream   ==   capacity   表頭   

前言

這兩天碰到面試題,說是頁面調度演算法,之前在作業系統書上有瞭解過,LRU(近期最少使用),還有OPT(最佳頁面替換演算法)、FIFO(先進先出頁面置換演算法),今天先來實現LRU 最近最少使用。

LRU 原理

LRU(Least recently used,最近最少使用)演算法根據資料的曆史訪問記錄來進行淘汰資料,其核心思想是“如果資料最近被訪問過,那麼將來被訪問的幾率也更高”。

參照網上的寫法,給出以下例子做個參考:

 1 #include <iostream> 2 #include <unordered_map>   3 #include <list>   4 #include <utility>   5 using namespace std; 6 using namespace stdext; 7  8 class LRUCache { 9 public:10     LRUCache(int capacity) {11         m_capacity = capacity;12     }13 14     int get(int key) {15         int retValue = -1;16         unordered_map<int, list<pair<int, int> > ::iterator> ::iterator it = cachesMap.find(key);17 18         //如果在Cashe中,將記錄移動到鏈表的最前端  19         if (it != cachesMap.end())20         {21             retValue = it->second->second;22             //移動到最前端  23             list<pair<int, int> > ::iterator ptrPair = it->second;24             pair<int, int> tmpPair = *ptrPair;25             caches.erase(ptrPair++);26             caches.push_front(tmpPair);27 28 29             //修改map中的值  30             cachesMap[key] = caches.begin();31         }32         return retValue;33     }34 35     void set(int key, int value) {36 37         unordered_map<int, list<pair<int, int> > ::iterator> ::iterator it = cachesMap.find(key);38 39         if (it != cachesMap.end()) //已經存在其中  40         {41             list<pair<int, int> > ::iterator ptrPait = it->second;42             ptrPait->second = value;43             //移動到最前面  44             pair<int, int > tmpPair = *ptrPait;45             caches.erase(ptrPait);46             caches.push_front(tmpPair);47 48 49             //更新map  50             cachesMap[key] = caches.begin();51         }52         else //不存在其中  53         {54             pair<int, int > tmpPair = make_pair(key, value);55 56 57             if (m_capacity == caches.size()) //已經滿  58             {59                 int delKey = caches.back().first;60                 caches.pop_back(); //刪除最後一個  61 62 63                                    //刪除在map中的相應項  64                 unordered_map<int, list<pair<int, int> > ::iterator> ::iterator delIt = cachesMap.find(delKey);65                 cachesMap.erase(delIt++);66             }67 68 69             caches.push_front(tmpPair);70             cachesMap[key] = caches.begin(); //更新map  71         }72     }73 74 75 private:76     int m_capacity;                                                                        //cashe的大小  77     list<pair<int, int> > caches;                                                  //用一個雙鏈表格儲存體cashe的內容  78     unordered_map< int, list<pair<int, int> > ::iterator> cachesMap;         //使用map加快尋找的速度  79 };80 81 82 int main(int argc, char **argv)83 {84     LRUCache s(2);85     s.set(2, 1);86     s.set(1, 1);87     cout << s.get(2) << endl;88     s.set(4, 1);89     s.set(5, 2);90     cout << s.get(5) << endl;91     cout << s.get(4) << endl;92     getchar();93     return 0;94 }

在vs 2015 進行運行 ,輸出:

 

解釋:程式首先會初始化2個儲存空間的LRUCache類,依次插進{2, 1 },{1,1} ,之後輸出 key=2 => value=1 ,之後插進 {4, 1} , 因為已經滿了所以替換掉最近沒有使用的{1 ,1} ,變成了 { 4,1} ,{2,1} ,之後又插進{5, 2} ,又替換掉了 {2,1} ,變成了 {4, 1} ,{5,2},然後輸出剩下兩個key,再重新排序誰最近使用過。

用到的知識是 : 雙鏈表 + 雜湊表 (使用map,內部元素自動排序;使用unordered_map內部不會進行有序排序)

頁面調度演算法(LRU)的原理 :緩衝機制中新資料或擊中的資料放到鏈表頭部,表示最近使用的資料,如果鏈表滿,從尾部淘汰資料。但只用鏈表會存在一個問題,擊中資料的時間複雜度為O(n),每次需要遍曆鏈表,所以引入雜湊表,時間複雜度降到O(1),以空間換時間。

 

LRU (近期最少使用)演算法 c++實現

相關文章

聯繫我們

該頁面正文內容均來源於網絡整理,並不代表阿里雲官方的觀點,該頁面所提到的產品和服務也與阿里云無關,如果該頁面內容對您造成了困擾,歡迎寫郵件給我們,收到郵件我們將在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.