1. Least Recently Used
最近最少使用淘汰機制, 訪問一個key在map中,也就是 在內存中, 就將此頁放到建表頭部, , 不在內存中, (假如規定鏈表只能有三個節點, 當訪問第四個時, 如果值不在內存中, 那就釋放鏈表最尾部的節點, 然後將此值包裝成節點, 放入頭部) 就先去磁盤取.
2. 爲什麼不使用雙向鏈表
使用雙向鏈表, 每個節點會增加兩個指針的空間消耗
3. redis不使用鏈表, 那用什麼結構或者屬性實現LRU淘汰策略
redis採用設置 全局 server-lruclock 時鐘, 每個節點有一個 lru時間戳 屬性, 類似於兩個時間戳
1. 訪問節點時候會將server-lruclock 複製給lru , 避免系統調用, 造成上下文切換
2. 而 全局的server-lruclock跟根據全局變量server.hz來調用系統操作實現更新
4. redis採用的一些內存策略
1. 定期刪除+惰性刪除
定期刪除 , 每隔一定時間, 根據maxmemory_samples設置的個數, 選取這麼多節點進行檢查過期, 一次性檢查全部, 會造成卡頓
惰性刪除, 你訪問一個key, 會看看過期沒, 過期了就刪除
4.1 那內存還是會滿怎麼辦, 那就出現淘汰策略
Redis系統提供五種淘汰策略,即參數maxmemory_policy有五種取值:
noeviction: 如果緩存數據超過了maxmemory限定值,並且客戶端正在執行的命令會導致內存分配,則向客戶端返回錯誤響應.
allkeys-lru: 所有的緩存數據(包括沒有超時屬性的和具有超時屬性的)都參與LRU算法淘汰.
volatile-lru: 只有超時屬性的緩存數據才參與LRU算法淘汰.
allkeys-random: 所有的緩存數據(包括沒有超時屬性的和具有超時屬性的)都參與淘汰, 但是採用隨機淘汰,而不是用LRU算法進行淘汰.
volatile-random: 只有超時屬性的緩存數據才參與淘汰,但是採用隨機淘汰,而不是用LRU算法進行淘汰.
volatile-ttl: 只有超時屬性的緩存數據才參與淘汰. 根據緩存數據的超時TTL進行淘汰,而不是用LRU算法進行淘汰.
4.2 怎樣實現LRU呢
根據3中描述的結構屬性, 全局屬性和節點私有兩個屬性差值越大說明, 最近最少訪問, 然後淘汰
如果淘汰策略是allkeys-random或者volatile-random,則從相應數據庫中隨機選擇一個key進行淘汰.
如果淘汰策略是allkeys-lru或者volatile-lru, 則根據配置的採樣值maxmemory_samples,隨機從數據庫中選擇maxmemory_samples個key, 淘汰其中熱度最低的key對應的緩存數據.
如果淘汰策略是volatile-ttl,則根據配置的採樣值maxmemory_samples,隨機從數據庫中選擇maxmemory_samples個key,淘汰其中最先要超時的key對應的緩存數據.
所以採樣參數maxmemory_samples配置的數值越大, 就越能精確的查找到待淘汰的緩存數據,但是也消耗更多的CPU計算,執行效率降
引用大佬~ https://blog.csdn.net/azurelaker/article/details/85045245