1. 程式人生 > >HBase RowKey雜湊和預分割槽

HBase RowKey雜湊和預分割槽

RowKey設計三大原則

1、雜湊原則,不要用類似於時間戳這樣的資料直接作為RowKey,如果確實需要用時間戳,可以把它放在低位,高位用雜湊來佔位。

2、長度原則,其實總結就一句話,rowkey只是一個唯一識別符號,並沒有更多的實際意義,所以不要搞得太長,但是,我想說但是,如果我的rowkey是有意義的,那麼讓他長一些是不是也可以呢?

3、唯一性原則,這一點沒什麼好說的,RowKey需要唯一確定一條資料,所以必須唯一。

後面2條原則沒什麼好說的,我們重點來看一下雜湊原則,為什麼會有這樣的建議。

在HBase當中,表會被劃分為1…n個Region,被託管在RegionServer中。Region二個重要的屬性:StartKey與EndKey表示這個 Region維護的rowKey範圍,當我們要讀/寫資料時,如果rowKey落在某個start-end key範圍內,那麼就會定位到目標region並且讀/寫到相關的資料。

如果我們在建表的時候,不預先設定好分割槽,隨著表內資料的增多,HBase會自動把表進行split,但是這樣做有幾點問題,第一,分割槽的原則,可能並不是我們想要的;第二,在表內資料相對較少的時候,無法充分展現分散式併發處理的優勢;第三,split操作,其實是比較耗資源的,如果資料增長過快,可能會相對頻繁的發生。

那麼,預分割槽又是如何實現的,我們看下面這個語句:

create 'testtable', 'common', 'data', {SPLITS => ['1','2','3']}

建好之後,我們可以在HBase的web頁面當中,看到表的分割槽的分佈情況:

這裡寫圖片描述

我們看到,我們用1,2,3三個數,把一個table劃分為了4個region,這四個region分別是:

x<1, 1<=x<2, 2<=x<3, 3<=x

那麼我們在insert的資料的時候,又該怎麼做呢?看下面的scala程式碼:

val p = new Put(Bytes.toBytes(String.valueOf(random.nextInt(4)) + new Date().getTime))

這句話是為一條新的資料,生成一個RowKey,那麼我們的key值由2部分組成,隨機雜湊+時間戳,其中隨機雜湊包括:【0,1,2,3】一共4個值,根據上面我們劃分的region,這4個值,將會對映到4個不同的region當中。