Redis淘汰策略詳解!

在這里插入圖片描述

目錄

    • 一、為什么需要淘汰策略? 🤔
    • 二、Redis 的淘汰策略詳解 👇
    • 三、如何選擇合適的淘汰策略? 🤔???
    • 四、如何切換 Redis 的淘汰策略? ??🔧
    • 五、總結 🎉

🌟我的其他文章也講解的比較有趣😁,如果喜歡博主的講解方式,可以多多支持一下,感謝🤗!

🌟了解 Redis 大 Key解決方案 請看 : Redis 大 Key:別讓你的 Redis 變成“胖子”!

其他優質專欄: 【🎇SpringBoot】【🎉多線程】【🎨Redis】【?設計模式專欄(已完結)】…等

如果喜歡作者的講解方式,可以點贊收藏加關注,你的支持就是我的動力
?更多文章請看個人主頁: 碼熔burning

一、為什么需要淘汰策略? 🤔

Redis 是一種基于內存的數據庫,速度飛快 🚀,但內存可是寶貴的資源!💰 當 Redis 實例使用的內存達到了你配置的上限 (maxmemory 指令設置的值) 時,就不能再無限制地存新數據了。如果不做處理,后續的寫入操作可能會導致 Redis 內存溢出 (OOM),甚至讓服務掛掉 💥。

為了優雅地處理這種情況,Redis 提供了多種內存淘汰策略。當內存告急 🚨 時,Redis 會根據你選定的策略,自動刪除一些“不那么重要”的鍵(Key),騰出空間來迎接新的數據。

注意: 如果你沒有設置 maxmemory (或者設為 0),Redis 會嘗試吃掉所有能用的內存,并且不會觸發任何淘汰策略。這種情況下,物理內存耗盡時,操作系統可能會出手干預,把 Redis 進程給“咔嚓”掉。😱

二、Redis 的淘汰策略詳解 👇

Redis 提供了以下幾種主要的淘汰策略 (可以通過 maxmemory-policy 配置項設置):

  1. noeviction (默認策略) 🙅?♀?

    • 行為: 當內存滿時,任何想寫入更多數據的命令(如 SET, LPUSH 等,但 DEL 和一些只讀命令除外)都會直接報錯 ?。它不會刪除任何現有鍵。
    • 含義: 就是不刪!寧可報錯,也絕不丟數據。
    • 適用場景:
      • 數據極其重要,一絲一毫都不能丟。
      • 應用層有完善的錯誤處理和降級機制。
      • 主要用作持久化存儲,而不是臨時緩存。
  2. allkeys-lru (Least Recently Used - 最近最少使用) ?

    • 行為: 內存不足時,在所有鍵中,把那個最久沒被訪問(讀或寫)的鍵給請出去。
    • 含義: 優先保留“熱乎”的數據,認為剛用過的以后還會用。
    • 適用場景:
      • 最常見、最通用的策略之一,適合絕大多數緩存場景 👍。
      • 你的應用訪問模式符合“熱點數據”原則(剛訪問的,可能馬上又會被訪問)。
      • 不知道選啥好的時候,選它一般沒錯。
  3. volatile-lru ?

    • 行為: 內存不足時,只在那些設置了過期時間 (TTL) 的鍵里,找那個最久沒被訪問的鍵淘汰掉。
    • 含義: 只在“臨時工”(設置了過期時間的鍵,通常是緩存)里搞淘汰,保護那些“正式工”(沒設過期時間的持久鍵)。
    • 適用場景:
      • 想明確區分緩存數據和需要長期保存的數據。
      • 把 Redis 同時當緩存(設 TTL)和少量持久存儲(不設 TTL)用。
  4. allkeys-random 🎲

    • 行為: 內存不足時,在所有鍵中,閉著眼睛隨機抓一個刪掉。🤷?♂?
    • 含義: 完全隨機,不看情面(訪問模式、過期時間)。
    • 適用場景:
      • 應用的訪問模式極其隨機,或者你壓根不在乎刪了哪個。
      • 對淘汰的精確性要求不高,追求極低的淘汰開銷。
      • 所有鍵的被訪問概率都差不多。
  5. volatile-random 🎰

    • 行為: 內存不足時,只在設置了過期時間 (TTL) 的鍵里,隨機抓一個刪掉。
    • 含義: 只在“臨時工”里隨機淘汰,保護“正式工”。
    • 適用場景:
      • volatile-lru 類似,想區分緩存和持久數據,但在緩存內部,訪問模式不重要或很隨機,用隨機淘汰省點力氣。
  6. volatile-ttl ?

    • 行為: 內存不足時,在設置了過期時間 (TTL) 的鍵里,找那個剩余壽命 (Time To Live) 最短 的鍵刪掉。
    • 含義: 優先淘汰那些馬上就要“壽終正寢”的鍵,可以認為它們價值最低。
    • 適用場景:
      • 緩存數據有明確的生命周期,希望先清理快到期的。
      • 希望緩存里盡量都是“新鮮出爐”的數據。
  7. allkeys-lfu (Least Frequently Used - 最不經常使用) 🔥 (Redis 4.0+ 新增)

    • 行為: 內存不足時,在所有鍵中,把那個訪問次數最少的鍵淘汰掉。
    • 含義: 優先保留“人氣王”(訪問頻率高的數據),認為訪問次數比最近訪問時間更能體現價值。LFU 會默默記錄每個鍵被訪問了多少次。
    • 適用場景:
      • 緩存場景中,有些數據可能偶爾才用,但一用就很關鍵(比如配置項);而有些數據可能短時間刷一波訪問量就沒用了。LFU 更擅長保留前者。
      • 訪問模式更符合“用得多就是爺”原則。
  8. volatile-lfu 👍 (Redis 4.0+ 新增)

    • 行為: 內存不足時,只在設置了過期時間 (TTL) 的鍵里,找那個訪問次數最少的鍵淘汰掉。
    • 含義: 只在“臨時工”里按訪問頻率淘汰,保護“正式工”,并優先保留人氣高的緩存。
    • 適用場景:
      • allkeys-lfu 類似,但需要保護沒設置過期時間的持久鍵。適合混合存儲,且緩存數據的訪問頻率是決定去留的關鍵。

💡 重要提示:近似 LRU 和 LFU

為了效率,Redis 實現的 LRU 和 LFU 都不是絕對精確的。它們用了近似算法:Redis 會隨機挑一小撮鍵(默認 5 個,通過 maxmemory-samples 參數配置),然后從這堆里面選出最符合策略(最老、最少用等)的那個來淘汰。樣本量越大,越接近精確,但 CPU 開銷也越大。對大多數應用,默認值就挺好用了!

三、如何選擇合適的淘汰策略? 🤔???

選哪個策略,得看你的應用場景和數據戲份:

  1. 通用緩存,不確定訪問模式?

    • 試試 allkeys-lru 吧!它是老牌明星,通常效果不錯。🌟
  2. 要區分緩存和持久數據?

    • 想保護沒設過期時間的“元老”鍵?用 volatile-lru, volatile-lfu, volatile-random, 或 volatile-ttl
    • 在這些 volatile-* 策略里:
      • 關心誰最近被翻牌子?選 volatile-lru ?。
      • 關心誰被翻牌子的次數最多?選 volatile-lfu 🔥 (Redis 4.0+)。
      • 想先送走快到期的?選 volatile-ttl ?。
      • 隨便刪個臨時的就行?選 volatile-random 🎰。
  3. 所有數據都是緩存,訪問頻率比時間更重要?

    • allkeys-lfu 🔥 (Redis 4.0+)。
  4. 所有數據都是緩存,訪問隨機或不 care 刪哪個?

    • allkeys-random 🎲。
  5. 數據寶寶一個都不能少,寧可寫入失敗?

    • noeviction 🙅?♀? (默認)。記得讓你的應用能處理好寫入錯誤哦!

四、如何切換 Redis 的淘汰策略? ??🔧

有兩種主要方式來設定或切換策略:

  1. 通過配置文件 (redis.conf) ??📄

    • 打開你的 redis.conf 文件。
    • 找到或加上 maxmemory-policy 這一行。
    • 把值改成你想要的策略名,比如:
      maxmemory-policy volatile-lru
      
    • 優點: 配置是永久的,Redis 重啟后還在。👍
    • 缺點: 改完需要重啟 Redis 服務才能生效。🔄
  2. 通過 CONFIG SET 命令 (動態修改) 💻?

    • 連上 Redis 服務器 (redis-cli)。
    • 執行 CONFIG SET 命令:
      CONFIG SET maxmemory-policy <policy_name>
      
      例如,切換到 allkeys-lfu
      CONFIG SET maxmemory-policy allkeys-lfu
      
    • 可以用 CONFIG GET maxmemory-policy 看看當前是啥策略。
    • 優點: 立刻生效,不用重啟 Redis,非常靈活!💨
    • 缺點: 這只是臨時修改。Redis 一重啟,就又變回 redis.conf 里寫的那樣了。😅
    • 讓動態修改“轉正”: 想讓動態修改永久生效?執行 CONFIG SET 之后,再執行 CONFIG REWRITE 命令。這會把當前運行的配置寫回 redis.conf 文件(前提是 Redis 有權限寫這個文件)。
# 示例:動態設置并永久保存
redis-cli
127.0.0.1:6379> CONFIG SET maxmemory-policy allkeys-lru
OK
127.0.0.1:6379> CONFIG REWRITE
OK

五、總結 🎉

理解和選擇對的 Redis 淘汰策略,對于優化性能、保證服務穩如老狗 🐕 以及滿足業務需求都超級重要!一定要根據你的應用特點和數據訪問模式來選型,并通過監控 Redis 內存 (INFO memory) 和淘汰情況 (INFO stats 里的 evicted_keys) 來看看效果怎么樣。記住,只有設置了 maxmemory,淘汰策略才會開始工作哦!😉

本文來自互聯網用戶投稿,該文觀點僅代表作者本人,不代表本站立場。本站僅提供信息存儲空間服務,不擁有所有權,不承擔相關法律責任。
如若轉載,請注明出處:http://www.pswp.cn/diannao/76983.shtml
繁體地址,請注明出處:http://hk.pswp.cn/diannao/76983.shtml
英文地址,請注明出處:http://en.pswp.cn/diannao/76983.shtml

如若內容造成侵權/違法違規/事實不符,請聯系多彩編程網進行投訴反饋email:809451989@qq.com,一經查實,立即刪除!

相關文章

存儲基石:深度解讀Linux磁盤管理機制與文件系統實戰

Linux系列 文章目錄 Linux系列前言一、磁盤1.1 初識磁盤1.2 磁盤的物理結構1.3 磁盤的存儲結構1.4 磁盤的邏輯結構 二、文件系統2.1 系統對磁盤的管理2.2 文件在磁盤中的操作 前言 Linux 文件系統是操作系統中用于管理和組織存儲設備&#xff08;如硬盤、SSD、USB 等&#xff…

本節課課堂總結

匿名子類&#xff1a; 說明 和 Java 一樣&#xff0c;可以通過包含帶有定義或重寫的代碼塊的方式創建一個匿名的子類。 單例對象&#xff08;伴生對象&#xff09; Scala語言是完全面向對象的語言&#xff0c;所以并沒有靜態的操作&#xff08;即在Scala中沒有靜態的概念&a…

I2C、SPI、UART、CAN 通信協議詳解

一、協議基本特性對比 特性ICSPIUARTCAN通信類型同步、半雙工同步、全雙工異步、全雙工異步、多主多從信號線SDA&#xff08;數據&#xff09;、SCL&#xff08;時鐘&#xff09;MOSI、MISO、SCK、SS&#xff08;片選&#xff09;TX&#xff08;發送&#xff09;、RX&#xff…

【diffusers 進階(十五)】dataset 工具,Parquet和Arrow 數據文件格式,load dataset 方法

系列文章目錄 【diffusers 極速入門&#xff08;一&#xff09;】pipeline 實際調用的是什么&#xff1f; call 方法!【diffusers 極速入門&#xff08;二&#xff09;】如何得到擴散去噪的中間結果&#xff1f;Pipeline callbacks 管道回調函數【diffusers極速入門&#xff0…

第十三章:持久化存儲_《鳳凰架構:構建可靠的大型分布式系統》

第十三章 持久化存儲 一、Kubernetes存儲設計核心概念 &#xff08;1&#xff09;存儲抽象模型 PersistentVolume (PV)&#xff1a;集群級別的存儲資源抽象&#xff08;如NFS卷/云存儲盤&#xff09;PersistentVolumeClaim (PVC)&#xff1a;用戶對存儲資源的聲明請求&#…

以太網安全

前言&#xff1a; 端口隔離可實現同一VLAN內端口之間的隔離。用戶只需要將端口加入到隔離組中&#xff0c;就可以實現隔離組內端口之間的二層數據的隔離端口安全是一種在交換機接入層實施的安全機制&#xff0c;旨在通過控制端口的MAC地址學習行為&#xff0c;確保僅授權設備能…

跨域問題前端解決

由于瀏覽器的同源策略&#xff0c;前后端分離的項目&#xff0c;調試的時候總是會遇到跨域的問題&#xff0c;這里通過修改前端代碼解決跨域問題。 首先先查看前端代碼的根目錄下&#xff0c;有沒有vue.config.js文件, 若有&#xff0c;使用方法1&#xff0c;若沒有此文件&…

Elasticsearch 報錯index_closed_exception

index_closed_exception 是 Elasticsearch 中的一個異常類型&#xff0c;它通常發生在嘗試對一個已經被關閉&#xff08;closed&#xff09;的索引執行搜索、寫入或其他操作時。在 Elasticsearch 中&#xff0c;索引是用來存儲和檢索數據的邏輯命名空間&#xff0c;可以將其類比…

LearnOpenGL-筆記-其九

今天讓我們完結高級OpenGL的部分&#xff1a; Instancing 很多時候&#xff0c;在場景中包含有大量實例的時候&#xff0c;光是調用GPU的繪制函數這個過程都會帶來非常大的開銷&#xff0c;因此我們需要想辦法在每一次調用GPU的繪制函數時盡可能多地繪制&#xff0c;這個過程就…

PDF預覽-搜索并高亮文本

在PDF.js中實現搜索高亮功能可以通過自定義一些代碼來實現。PDF.js 是一個通用的、基于Web的PDF閱讀器&#xff0c;它允許你在網頁上嵌入PDF文件&#xff0c;并提供基本的閱讀功能。要實現搜索并高亮顯示文本&#xff0c;你可以通過以下幾個步驟來完成&#xff1a; 1. 引入PDF…

二叉樹——隊列bfs專題

1.N叉樹的層序遍歷 我們之前遇到過二叉樹的層序遍歷&#xff0c;只需要用隊列先進先出的特性就可以達到層序遍歷的目的。 而這里不是二叉樹&#xff0c;也就是說讓節點的孩子入隊列時不僅僅是左右孩子了&#xff0c;而是它的所有孩子。而我們看這棵多叉樹的構造&#xff0c;它…

Python高級爬蟲之JS逆向+安卓逆向1.1節-搭建Python開發環境

目錄 引言&#xff1a; 1.1.1 為什么要安裝Python? 1.1.2 下載Python解釋器 1.1.3 安裝Python解釋器 1.1.4 測試是否安裝成功 1.1.5 跟大神學高級爬蟲安卓逆向 引言&#xff1a; 大神薯條老師的高級爬蟲安卓逆向教程&#xff1a; 這套爬蟲教程會系統講解爬蟲的初級&…

Windows 安裝和使用 ElasticSearch

SpringBoot3 整合 Elasticsearch 1. ElasticSearch 1.1 ES &#xff08;1&#xff09;ES 是一個開源的分布式搜索和分析引擎&#xff0c;專為處理大模型數據而設計&#xff0c;它能夠實現近乎實時的數據檢索、分析和可視化&#xff0c;廣泛用于全文搜索、日志分析和監控&…

matplotlib初探

庫引入 import matplotlib.pyplot as pltpyplot.figure 創建新圖形或激活現有圖形

NVM 多版本Node.js 管理全指南(Windows系統)

&#x1f9d1; 博主簡介&#xff1a;CSDN博客專家、全棧領域優質創作者、高級開發工程師、高級信息系統項目管理師、系統架構師&#xff0c;數學與應用數學專業&#xff0c;10年以上多種混合語言開發經驗&#xff0c;從事DICOM醫學影像開發領域多年&#xff0c;熟悉DICOM協議及…

實驗室預約|實驗室預約小程序|基于Java+vue微信小程序的實驗室預約管理系統設計與實現(源碼+數據庫+文檔)

實驗室預約小程序 目錄 基于微信小程序的實驗室預約管理系統設計與實現 一、前言 二、系統功能設計 三、系統實現 1、微信小程序前臺 2、管理員后臺 &#xff08;1&#xff09;管理員登錄 &#xff08;2&#xff09;實驗室管理 &#xff08;3&#xff09;公告信息管理…

SpringBoot底層-數據源自動配置類

SpringBoot默認使用Hikari連接池&#xff0c;當我們想要切換成Druid連接池&#xff0c;底層原理是怎樣呢 SpringBoot默認連接池——Hikari 在spring-boot-autoconfiguration包內有一個DataSourceConfiguraion配置類 abstract class DataSourceConfiguration {Configuration(p…

面試算法高頻03-遞歸

認識遞歸 遞歸的概念與特性&#xff1a;遞歸本質類似循環&#xff0c;是通過函數體進行的循環操作。借助電影《盜夢空間》類比&#xff0c;遞歸如同主角在不同夢境層穿梭&#xff0c;向下進入不同遞歸層&#xff0c;向上能回到原來一層&#xff0c;每一層環境和周圍元素相似&a…

linux Gitkraken 破解

ubuntu 安裝 Gitkraken 9.x Pro 版本_gitcracken.git-CSDN博客

設計模式簡述(十一)裝飾器模式

裝飾器模式 描述基本使用使用 描述 裝飾器模式是一種功能型模式 用于動態增強對象的功能 這么一說感覺上和代理模式有些類似 抽象裝飾器 要實現原有業務接口&#xff0c;并注入原有業務對象 至于對原有業務對象的調用&#xff0c;可以采用private業務對象 實現業務接口方法的…