進程內緩存與redis比較

在後端系統中,因爲數據庫讀寫性能所限,性能瓶頸每每出如今數據庫上,爲了下降數據庫訪問壓力,能夠採起的方式有緩存、數據庫讀寫分離、分表等數據庫

其中,對於數據庫讀取壓力過大的狀況,緩存能夠說是首選解決方式後端

緩存按照數據存儲位置來區分,緩存能夠分爲兩種: 進程內緩存與進程外緩存緩存

  • 進程內緩存: 最簡單的能夠直接用語言內的散列表(Java HashMap,Python字典 等),或者一些功能更完善的第三方庫網絡

  • 進程外緩存: 常見的如Redis,Memcache等session

下面的表格是二者之間一些優缺點的對比, 下文將逐條分析這些優缺點負載均衡

/ 進程內緩存 Redis
水平擴展 困難 簡單
可靠/易用 沒有過時,內存淘汰等 可靠
訪問速度 直接操做變量,延遲低 須要網絡傳輸和序列化
可否保存引用類型 能夠保存引用類型 只能存字符串

進程內緩存缺點

缺點1. 不利於水平擴展

如今的後端程序每每是須要多個節點進行負載均衡對外提供服務的,而進程內緩存只有本節點可以訪問性能

在這種場景下,若是使用了進程內緩存,那麼也就意味着每一個節點有它本身的"狀態",致使在A節點更改了緩存,而B節點緩存數據並不會發生變動,這時再從B節點讀取就會獲得沒有更改過的舊數據,與A節點不一致code

這種不一致有以下解決方式:cdn

方式1: 同步數據

  • 方式: 當在某個節點中更新緩存時,將數據變化同步到所有其餘節點
  • 缺點:
    1. 一樣的數據在每個節點都有一份拷貝,浪費內存
    2. 同步的延遲不肯定,可能在修改後的一段時間內沒有完成同步,讀到舊數據
    3. 同步的數據量大,網絡開銷多;隨着節點數N的增加,由於要同步到每個其餘節點,發送N-1份數據,難以接受
    4. 因爲這種方式至關於有多個可寫的主節點,同步時會致使數據 不一致 (先更改的值可能覆蓋後更改的) 以下圖所示:
      在這裏插入圖片描述

方式2: 黏性session:

在上面列出的幾個缺點中,多節點寫入致使的數據不一致問題是最嚴重的對象

面對這種問題,能夠經過將對同一個鍵的寫操做都發到同一個節點來避免

  • 方式: 在負載均衡時發到指定的節點
  • 缺點: 負載均衡服務須要處理額外的邏輯,實現複雜

缺點2. 可靠性不高,功能不全

Redis提供了鍵過時,定時清理,內存淘汰等功能,支持多種淘汰策略;而且通過多年大規模的使用,可靠性很高

進程內緩存的另外一個問題就是比較簡陋,每每不具有這些功能,可能須要本身處理內存溢出等狀況,無疑比較困難


進程內緩存優勢

優勢1. 訪問速度更快

因爲客戶端和Redis之間須要等待網絡通訊的延遲,而且對數據要作額外的序列化和反序列化處理,因此訪問速度天然低於直接訪問內存變量的進程內緩存

優勢2. 能夠保存引用類型

進程內緩存的另外一個優勢就是能夠保存引用類型,而Redis實際上只能存字符串,這在某些場景中是很是有用的

例如: 緩存定時任務的對象

業務中經常須要讓一個任務在某個時間點執行,並可能在執行以前進行取消; 這時候使用進程內緩存保存定時任務的對象就能夠很方便的執行對象上的取消定時任務方法了,而使用Redis則難以作到這一點

總結

Redis之類的進程外緩存功能比較完善,通常狀況下直接使用它便可

可是進程內緩存在某些場景中也頗有用處,例如:

  1. 數據相對固定: 對於不怎麼變化的數據,不在乎更新數據致使的一致性問題, 使用進程內緩存能夠獲取更快的訪問速度,避免網絡和序列化開銷
  2. 須要緩存引用類型
相關文章
相關標籤/搜索