1. 程式人生 > >Redis一致性雜湊演算法

Redis一致性雜湊演算法

場景描述

假設有N臺快取伺服器,現在我們希望把3萬張圖片快取到這些伺服器上。目標:快取儘可能均勻分佈在各伺服器上,以上它們能夠平攤快取壓力。那麼可以:

  • 無任何規律的將3萬張圖片平均快取到所有伺服器上。但當需訪問某圖片時,需要遍歷所有伺服器所有快取項,效率太低、時間太長。
  • hash(快取項的KEY)%伺服器的個數,決定快取項被快取到哪一臺伺服器上(快取項KEY可取名字等)。查詢的時候,同樣根據該算式,就可知道應該到哪一臺伺服器上去找。
    缺點:當增刪伺服器時,會引起大量快取項的快取位置發生變化,從而會導致由於大量快取在同一時間失效,造成快取雪崩。

為了解決方案二中的缺陷,就有了一致性雜湊演算法。

原理

  • 假設有一個圓環,環上有2^32個點,從0 ~ 2^32-1
  • hash(伺服器IP) % 2^32,將各伺服器對映到環上
  • hash(快取項的KEY) % 2^32,將各快取項對映到環上
  • 從快取項的位置開始,沿著順時針方向遇到的第一個伺服器,就是快取項的快取位置

優點

刪除某伺服器後,只需移動原本儲存在該伺服器的快取項,而不會改變其他快取項的快取位置(即:只會導致部分快取項在同一時間內失效)。移動後位置:從該伺服器觸發,沿順時針方向遇到的第一個伺服器。

缺陷

在介紹原理時,是假設所有伺服器被均勻對映到環上,但實際情況可能是:所有伺服器被密集對映在同一區域,從而可能導致大量快取項被快取在同一伺服器上。那麼當該伺服器出現故障,同樣可能造成快取雪崩。

改進方法

  • 為每一個伺服器生成多個虛擬節點,並對映到環上。虛擬節點越多,快取分配越均勻
  • 虛擬節點的hash計算,可以採用實際伺服器的IP地址加數字字尾的方式,如Hash(“192.168.1.100#1”) % 2^32