hbase概念

1. 概述(扯淡~)數據庫

HBase是一幫傢伙看了Google發佈的一片名爲「BigTable」的論文之後,猶如醍醐灌頂,進而「山寨」出來的一套系統。緩存

因而可知:分佈式

  1. 幾乎全部的HBase中的理念,均可以從BigTable論文中獲得解釋。原文是英語的,並且還有很多數學概念,看了有點兒懵,建議網上找找學習筆記看看,差很少也就能夠入門了。oop

  2. Google確實牛X。性能

  3. 老外也愛山寨~學習

 

第一次看HBase, 可能看到如下描述會懵:「基於列存儲」,「稀疏MAP」,「RowKey」,「ColumnFamily」。google

其實沒那麼高深,咱們須要分兩步來理解HBase, 就可以理解爲何HBase可以「快速地」「分佈式地」處理「大量數據」了。spa

  1.內存結構翻譯

  2.文件存儲結構設計

 

2. 名詞概念以及內存結構

  假設咱們有一張表(其中只有一條數據):

RowKey

ColumnFamily : CF1

ColumnFamily : CF2

TimeStamp

Column: C11

Column: C12

Column: C21

Column: C22

「com.google」

「C11 good」

「C12 good」

「C12 bad」

「C12 bad」

T1

 

 

 

 

 

 

 

  1) RowKey: 行鍵,可理解成MySQL中的主鍵列。

  2) Column: 列,可理解成MySQL列。

  3) ColumnFamily: 列族, HBase引入的概念:

    1. 將多個列聚合成一個列族。
    2. 能夠理解成MySQL的垂直分區(將一張寬表,切分紅幾張不那麼寬的表)。
    3. 此機制引入的緣由,是由於HBase相信,查詢可能並不須要將一整行的全部列數據所有返回。(就像咱們每每在寫SQL時不太會寫select all同樣)
    4. 對應到文件存儲結構(不一樣的ColumnFamily會寫入不一樣的文件)。

  4) TimeStamp:在每次跟新數據時,用以標識一行數據的不一樣版本(事實上,TimeStamp是與列綁定的。)

 

那咱們爲什麼會獲得HBase的讀寫高性能呢?其實全部數據庫操做如何獲得高性能,答案几乎都是一致的,就是作索引。

HBase的設計拋棄了傳統RDBMS的行式數據模型,把索引和數據模型原生的集成在了一塊兒。

以上圖的表爲例,表數據在HBase內部用Map實現,咱們把它寫成JSon的Object表述,即:

複製代碼
{
  "com.google": { CF1: { C11:{ T1: good } C12:{ T1: good } CF2: { C21:{ T1: bad } C22:{ T1: bad } } } }
複製代碼

 

因爲Map自己能夠經過B+樹來實現,因此隨機訪問的速度大大加快(咱們須要想象一下,表中有不少行的狀況)。

如今咱們在原來的表上修改一下(將Column: C22改成」good」):

RowKey

ColumnFamily : CF1

ColumnFamily : CF2

TimeStamp

Column: C11

Column: C12

Column: C21

Column: C22

「com.google」

「C11 good」

「C12 good」

「C12 bad」

「C12 bad」

T1

「com.google」

「C11 good」

「C12 good」

「C12 bad」

「C12 good」

T2

 

 

 

 

 

 

 

 

 

因而MAP變爲了:

複製代碼
{
  "com.google": { CF1: { C11:{ T1: good } C12:{ T1: good } CF2: { C21:{ T1: bad } C22:{ T1: bad T2:good } } } }
複製代碼

事實上,咱們只須要在C22的object再加一個屬性便可。若是咱們把這個MAP翻譯成表形狀,也能夠表示爲:

RowKey

ColumnFamily : CF1

ColumnFamily : CF2

TimeStamp

Column: C11

Column: C12

Column: C21

Column: C22

「com.google」

「C11 good」

「C12 good」

「C12 bad」

「C12 bad」

T1

 

 

 

 

「C12 good」

T2

 

 

 

 

 

 

 

 

 

咱們發現,這個表裏不少列是沒有value的。想象一下,若是再加入一行RowKey不一樣的數據,其中Column:C11內容爲空,就能夠在Json中省略該屬性了。

好了,扯了這麼多,就是爲了說明HBase是「稀疏的高階MAP」。

爲了查詢效率,HBase內部對RowKey作了排序,以保證相似的或者相同的RowKey都集中在一塊兒,因而HBase就變成了一張「稀疏的,有序的,高階的MAP」。有沒有以爲這樣的表述很高冷? :)

 

3. 文件存儲結構與進程模型

如上所述,HBase是一張「稀疏的,有序的,高階的MAP」。

一般來講,MAP能夠用B+樹來實現。B+樹對查詢性能而言表現良好,可是對插入數據有些力不從心,尤爲對於插入的數據須要持久化到磁盤的狀況而言。

咱們對RowKey作了排序,爲了保證查詢效率,咱們但願將連續RowKey的數值保存在連續的磁道上,以免大量的磁盤隨機尋道。因此在插入數據時,對於B+樹而言,就面臨着大量的文件搬移工做。

HBase使用了LSM樹實現了MAP,簡單說來,就是將插入/修改操做緩存在內存中,當內存中積累足夠的數據後,再以塊的形式刷入到磁盤上。

 

HBase的進程模型:

 

Region: 基於RowKey的分區,可理解成MySQL的水平切分。

每一個Region Server就是Hadoop集羣中一臺機器上的一個進程。

好比咱們的有1-300號的RowKey, 那麼1-100號RowKey的行被分配到Region Server 1上,一樣,101-200號分配到Region Server 2上, 201-300號分配到Region Server 3上。

在內存模型中,咱們說RowKey保證了相鄰RowKey的記錄被連續地寫入了磁盤。在這裏,咱們發現,RowKey決定了行操做(增,刪,改,查)會被交與哪臺Region Server操做。

讓咱們假設一下,若是咱們的RowKey以記錄的TimeStamp起始,從內存模型上說,這很合理,由於咱們可能面臨大量的用戶流水記錄查詢,查詢的條件會設置一個時間片斷,咱們但願一次性從磁盤中讀取這些流水記錄,從而避免頻繁的磁盤尋道操做。

可是再另外一方面,用戶的流水記錄查詢會很頻繁的出現「截至到至今」的查詢條件,依照咱們上面的進程模型,Region Server 3必定會被分配到(由於最近的記錄排在最後),這樣就可能形成Region Server 3的「過熱」,而Region Server 1「過冷」的狀況。

 

文件存儲模型:

在HDFS中,每張表對應一個目錄,在表目錄下,每一個Region對應一個目錄,在Region目錄下,每一個Store對應一個目錄(一個Store對應一個ColumFamily)。結構以下:

HBase

  |

  ---Table

       |

       ---XXXX(Region的hash)

       |    |

       |    ----ColumnFamily

       |              |

       |              ---文件

       |

       ---YYYYY(另外一個Region的hash)

 

咱們的新發現是,不一樣的ColumnFamily對應不一樣的Store, 而且被寫入了不一樣的目錄, 這意味着:

1. 經過將一張表分解成了不一樣的ColumnFamily,HBase能夠從磁盤一次讀取更少的內容(IO操做每每是計算機系統中最慢的一環)。

2. 咱們不該該將須要一次查詢出的列,分解在不一樣的ColumnFamily中,不然覺得着HBase不得不讀取兩個文件來知足查詢要求。

 

另外,一個ColumnFamily中的每一列是連續存儲的。即若是一個ColumnFamily中存在C1,C2兩列,一段具備100行記錄的存儲格式是:

C1(1),C2(1),C1(2),C2(2),C1(3),C2(3).............C1(100),C2(100)

與其說HBase是基於列的數據庫,更不如說HBase是基於「列族」的數據庫。

 

4 理解:

基於以上的模型,大體的理解是:

1. RowKey決定了行操做任務進入RegionServer的數量,咱們應該儘可能的讓一次操做調用更多的Region Server,已達到分佈式的目的。

2. RowKey決定了查詢讀取連續磁盤塊的數量,最理想的狀況是一次查詢,在每一個Region Server上,只讀取一個磁盤塊。

3. ColumnFamily決定了一次查詢須要讀取的文件數(不一樣的文件不只意味着分散的磁盤塊,還意味着屢次的文件打開關閉操做)。咱們應儘可能將但願查詢的結果集合併到一個ColumnFamily中。同時儘可能去除該ColumnFamily中不須要的列。

4. HBase官方建議儘可能的減小ColumnFamily的數量。

 

再瞎總結一下:

1. RowKey由查詢條件決定。

2. ColumnFamily由查詢結果決定。

相關文章
相關標籤/搜索