目錄
筆記來自分布式原理一書,供個人學習。
數據分布
單機系統與分布式系統的最大的區別在於問題的規模,即計算、存儲的數據量的區別。將一個單機問題使用分布式解決,首先要解決的就是如何將問題拆解為可以使用多機分布式解決,使得
分布式系統中的每台機器負責原問題的一個子集。由於無論是計算還是存儲,其問題輸入對象都是數據,所以如何拆解分布式系統的輸入數據成為分布式系統的基本問題,我們稱這樣的數據拆解為數據分布方式。
哈希方式
哈希方式是最常見的數據分布方式,其方法是按照數據的某一特征計算哈希值,並將哈希值與機器中的機器建立映射關系,從而將不同哈希值的數據分布到不同的機器上。所謂數據特征可以是
key-value 系統中的 key,也可以是其他與應用業務邏輯相關的值。例如,一種常見的哈希方式是按數據屬於的用戶 id 計算哈希值,集群中的服務器按0到機器數減 1 編號,哈希值除以服務器的個數,結果的余數作為處理該數據的服務器編號。工程中,往往需要考慮服務器的副本冗余,將每數台(例如 3)服務器組成一組,用哈希值除以總的組數,其余數為服務器組的編號。圖 2-1 給出了哈希方式分數據的一個例子,將數據按哈希值分配到 4 個節點上。
哈希方式特點:
1.每個節點只計算一部分數據;每個節點只存儲一部分數據。
我們假設節點的數量沒有變化(實際上不可能),那么同一個用戶的數據會被同一個節點計算和存儲。
2.任何節點只需要知道哈希函數的計算方式及模的服務器總數就可以計算出處理具體數據的機器是哪台。
哈希方式只需要知道兩個關鍵:1.以什么作為哈希計算的特征值;2.節點數量(節點數量,因為節點數量是動態的,必需有保活機制,服務發現等)。就可以計算這個數據由哪個節點處理。
缺點:
1.擴展性:一旦節點數量發生變化,則幾乎所有的數據需要被遷移並重新分布。
分布式系統中,節點的添加和刪除、或者宕機等是很普遍的情況,當節點數量發生變化,同一個ID的數據會由不同的節點處理。
2.“數據傾斜”(dataskew)問題:一旦某數據特征值的數據嚴重不均。
如果某用戶的數據量過大,該用戶的數據始終由某一台節點處理。假如該用戶的數據量超過了單台服務器處理能力的上限,則該用戶的數據不能被處理。
問題解決:
關於擴展性:
1.擴展哈希分布數據的系統時,往往使得集群規模成倍擴展,按照數據重新計算哈希,這樣原本一台機器上的數據只需遷移一半到另一台對應的機器上即可完成擴展。
2.還有一種思路是不再簡單的將哈希值與機器做除法取模映射,而是將對應關系作為元數據由專門的元數據服務器管理。訪問數據時,首先計算哈希值並查詢元數據服務器,獲得該哈希值對應的機器。缺點是需要以較復雜的機制維護大量的元數據,但是元數據中哈希值和對應的機器的值不是固定的,所以可以做負載均衡。
關於數據傾斜問題:
1.一種極端的思路是,使用數據的全部而不是某些維度的特征計算哈希,這樣數據將被完全打散在集群中。然而實踐中有時並不這樣做,這是因為這樣做使得每個數據之間的關聯性完全消失,一個用戶ID的數據可能分布到任何一台機器處理。只適用於數據之間沒有聯系。
3、一致性哈希方式
一致性哈希(consistent hashing)是另一個種在工程中使用較為廣泛的數據分布方式。一致性哈希最初在 P2P 網絡中作為分布式哈希表(DHT)的常用數據分布算法。一致性哈希的基本方式是使用一個哈希函數計算數據或數據特征的哈希值,令該哈希函數的輸出值域為一個封閉的環,即哈希函數輸出的最大值是最小值的前序。將節點隨機分布到這個環上,每個節點負責處理從自己開始順時針至下一個節點的全部哈希值域上的數據。
一致性哈希方式特點:
前面哈希分布數據的方式在集群擴容時非常復雜,往往需要倍增節點個數,與此相比,一致性哈希的優點在於可以任意動態添加、刪除節點,每次添加、刪除一個節點僅影響一致性哈希環上相鄰的節點。
缺點:
1.隨機分布節點的方式使得很難均勻的分布哈希值域,尤其在動態增加節點后,即使原先的分布均勻也很難保證繼續均勻
2.當一個節點異常時,該節點的壓力全部轉移到相鄰的一個節點,當加入一個新節點時只能為一個相鄰節點分攤壓力。
問題解決:
關於分布不均勻與負載均衡:
系統初始時就創建許多虛節點,
虛節點的個數一般遠大於未來集群中機器的個數,將虛節點均勻分布到一致性哈希值域環上,其功能與基本一致性哈希算法中的節點相同。為每個節點分配若干虛節點。操作數據時,首先通過數據的哈希值在環上找到對應的虛節點,進而查找元數據找到對應的真實節點。使用虛節點改進有多個優點。首先,一旦某個節點不可用,該節點將使得多個虛節點不可用,從而使得多個相鄰的真實節點負載失效節點的壓里。同理,一旦加入一個新節點,可以分配多個虛節點,從而使得新節點可以負載多個原有節點的壓力,從全局看,較容易實現擴容時的負載均衡。
以下轉載:https://blogread.cn/it/article/3833?f=sr
一致性哈希算法:
一致性哈希也只是提出四個概念和原則:
1、balance:哈希結果盡可能的平均分散到各個節點上,使得每個節點都能得到充分利用。
2、Monotonicity:上面也說了,如果是用哈希算法,節點變更會使得整個網絡的映射關系更改。如果是carp,會使得1/n的映射關系更改。一致性哈希的目標,是節點變更,不會改變網絡的映射關系。
3、spread:同一份數據,存儲到不同的節點上,換言之就是系統冗余。一致性哈希致力於降低系統冗度。
4、load:負載分散,和balance其實是差不多的意思,不過這里更多是指數據存儲的均衡,balance是指訪的均衡。
Chord算法:
一致性哈希有多種實現算法,最關鍵的問題在於如何定義數據分割策略和節點快速查詢。
chord算是最為經典的實現。cassandra中的DHT,基本是chord的簡化版。
網絡中每個節點分配一個唯一id,可以通過機器的mac地址做sha1,是網絡發現的基礎。
假設整個網絡有N 個節點,並且網絡是呈環狀。兩個節點間的距離定義為每個節點會存儲一張路由表(finger表),表內順時針按照離本節點2、4、8、16、32.……2i的距離選定log2N個其他節點的ip信息來記錄。
存儲方面:數據被按一定規則切割,每一份數據也有一個獨立id(查詢key),並且和節點id的值域是一樣的。然后查找節點,如果存在和數據id一樣的節點id,則將這份數據存在該節點上;如果不存在,則存儲到離該數據id距離最近的節點上。同時,為了保證數 據的可靠性,會順時針往下找K個冗余節點,存儲這份數據。一般認為K=3是必須的。
查詢方面:先從自己的路由表中,找一個和數據id距離最近、並且存活在網絡中的節點next。如果該節點的 id巧合和數據id相等,那么恭喜你。如果不相等,則到next進行遞歸查找。一般或需要經過多次查詢才能找到數據所在的節點,而這個次數是可以被證明小 於等於log2N的。
在這個查詢的過程中就體現了路由表的選取優勢了,其實是實現了一個二分查找,從每個節點來觀察網絡,都是將網絡分成了log2N塊,最大一塊里面有N/2個節點。路由表里面其實是記錄了每一塊的第一個節點。這樣每一次查詢,最少排除了一半的節點。保證在 log2N次內找到目標節點。
新增一個節點i,需要預先知道網絡中已經存活的一個節點j,然后通過和節點j交互,更新自己和其他節點的路由表。並且,需要將離自己距離最近的節點中的數據copy過來,以提供數據服務。
損失一個節點,路由算法會自動跳過這個節點,並且依靠數據的冗余來持續提供服務。
KAD算法(Kademlia)
kad算法其實是在chord上做的優化。主要是兩個點:
1、用二進制(32/64/128)表示一個節點的id,兩節點的id異或運算得到節點間的距離。
2、 每個節點保持的路由信息更豐富,同樣是將整個網絡按照划分成log2N份,在chord中,是保持log2N個路由節點,但在kad里面,是保存了 log2N個隊列。每個隊列長度為配置值K,記錄網絡中對應節點區域的多個節點,並且根據活躍時間對這些節點進行換入換出。
第一點是方便進行網絡划分,節點按照二進制中每一bit的0或1建成一棵二叉樹。
第二點是使得節點查詢更迅速。從分割情況我們就可以得知,最壞情況不會差於chord,但保存更多的節點使得命中概率更高。另外隊列中根據活躍時間進行換入換出,更有利於在p2p這種節點變更頻繁的網絡中快速找到有效的節點。
關於kad的介紹,這篇文章講的比較詳細wenku.baidu.com/view/ee91580216fc700abb68fcae.html