Kylin實戰 建立cube的優化

2021-09-28 18:04:17 字數 3948 閱讀 9587

背景

kylin的維度組合優化

1、 mandatory維度

2、 hierarchy維度

3、 derived維度

4、 聯合維度

kylin的rowkey優化

1、編碼

2、順序

3、分片

了解olap cube的人都會知道,建立cube的過程中往往會出現「維度**」問題。kylin是典型的multidimensional olap應用,犧牲靈活性,使用預計算來提公升效能,以實現對超大資料集的秒級響應。在kylin建立cube的過程中,如果預設選擇所有維度的組合,那麼維度組合將是2^n(n為維度個數)。

在工業領域,一般建立的寬表可能會有大幾十個的維度,甚至達到上百。但是平常使用的時候,也許只有不到一半的維度組合能超過20個維度。大部分維度組合的個數可能都是10多個。這樣一來,會造成儲存的極大浪費,也會影響kylin的查詢效能。

kylin從1.5版本後引入了乙個新的特性:聚合組(aggregation groups)。

如下是官網提出的兩種方法:

1、首先,我們可以移除那些不一定是維度的維度。例如,假設有乙個日期查詢表,其中儲存的cal_dt是pk列,以及許多派生列,如week_begin_dt、month_begin_dt。儘管分析人員需要week_begin_dt作為維度,但我們可以對它進行刪減,因為它總是可以從維度cal_dt中計算出來,這就是「派生」優化。

2、其次,可以修剪聚合組之間的某些組合。這是本文的主要討論,我們稱之為「組合修剪」。例如,如果將某個維度指定為「強制」,則可以刪除所有沒有該維度的組合。如果維a,b,c形成「層次」關係,則僅保留與a,ab或abc的組合。在v1.5之前,kylin還具有「聚合組」概念,該概念也可用於組合修剪。但是,它的文獻記錄不多,很難理解(我也發現很難解釋)。無論如何,我們將跳過它,因為我們將重新定義「聚合組」的真正含義。

下文主要講解第二種方法-----維度剪枝優化:

在kylin1.5之後,有四種型別的聚合組,每一種型別的聚合組也即是一種特定的規則。通過這四種規則來達到剪枝優化的目的。

這種維度意味著每次查詢的group by中都會攜帶的,將某乙個dimension設定為mandatory可以將cuboid的個數減少一半,如下圖:

這是因為我們確定每一次group by都會攜帶a,那麼就可以省去所有不包含a這個維度的cuboid了。

這種維度是最常見的,尤其是在mondrian中,我們對於多維資料的操作經常會有上捲下鑽之類的操作,這也就需要要求維度之間有層級關係,例如國家、省、城市,年、季度、月等。有層級關係的維度也可以大大減少cuboid的個數。如下圖:

這裡僅僅侷限於a/b/c是乙個層級,例如a是年份,b是季度、c是月份,那麼查詢的時候可能的組合只有年、xx年的季度、xx年xx季度的xx月,這就意味著我們不能再單獨的對季度和月份進行聚合了,例如我們查詢的時候不能使用group by month,而必須使用group by year,quart,month。如果需要單獨的對month進行聚合,那麼還需要再使用month列定義乙個單獨的普通維度。

這類維度的意思是可推導的維度,需要該維度對應的乙個或者多個列可以和維度表的主鍵是一對一的,這種維度可以大大減少cuboid個數,如下圖:

例如timeid是時間這個維度表的主鍵,也就是事實表的外來鍵,時間只精確到天,那麼year、month、day三列可以唯一對應著乙個time_id,而time_id是事實表的外來鍵,那麼我們可以指定year、month、day為乙個derived維度,實際儲存的時候可以只根據timeid的取值決定維度的組合,但這就要求我們在查詢的時候使用的group by必須指定derived維度集合中的所有列。 3.聯合維度(joint) 每乙個聯合維度包括兩個或者更多的維度,聯合維度內的維度,要麼不出現,要麼必須一起出現。不同的聯合之間不應當有共同的維度

聯合維度:將幾個維度視為乙個維度。 適用場景:

優化效果:將n個維度設定為聯合維度,則這n個維度組合成的cuboid個數會從2的n次方減少到1。

應用例項:

假設建立乙個交易資料的cube,它具有很多普通的維度,像是交易日期 cal_dt,交易的城市 city,顧客性別 ***_id 和支付型別 pay_type 等。分析師常用的分析方法為通過按照交易時間、交易地點和顧客性別來聚合,獲取不同城市男女顧客間不同的消費偏好,例如同時聚合交易日期 cal_dt、交易的城市 city 和顧客性別 ***_id來分組。 聚合組:[cal_dt, city, ***_id,pay_type] 聯合維度: [cal_dt, city, ***_id]

case 1:

select cal_dt, city, ***_id, count(*) from table group by cal_dt, city, ***_id

則它將從cuboid [cal_dt, city, ***_id]中獲取資料

複製**

case2:

如果有一條不常用的查詢:

kylin 以 key-value 的方式將 cube 儲存到 hbase 中,hbase 的 key,也就是 rowkey,是由各維度的值拼接而成的;為了更高效地儲存這些值,kylin 會對它們進行編碼和壓縮;每個維度均可以選擇合適的編碼(encoding)方式,預設採用的是字典(dictionary)編碼技術;字段支援的基本編碼型別如下:

boolean:適用於字段值為true, false, true, false, true, false, t, f, t, f, yes, no, yes, no, yes, no, y, n, y, n, 1, 0;

integer:適用於字段值為整數字元,支援的整數區間為[ -2^(8n-1), 2^(8n-1)];

date:適用於字段值為日期字元,支援的格式包括yyyymmdd、yyyy-mm-dd、yyyy-mm-dd hh:mm:ss、yyyy-mm-dd hh:mm:ss.sss,其中如果包含時間戳部分會被截斷;

time:適用於字段值為時間戳字元,支援範圍為[ 1970-01-01 00:00:00, 2038/01/19 03:14:07],毫秒部分會被忽略,time編碼適用於 time, datetime, timestamp 等型別;

fix_length:適用於超高基場景,將選取欄位的前 n 個位元組作為編碼值,當 n 小於字段長度,會造成字段截斷,當 n 較大時,造成 rowkey 過長,查詢效能下降,只適用於 varchar 或 nvarchar 型別;

fixed_length_hex:適用於字段值為十六進製制字元,比如 1a2bff 或者 ff00ff,每兩個字元需要乙個位元組,只適用於 varchar 或 nvarchar 型別。

各維度在 rowkeys 中的順序,對於查詢的效能會產生較明顯的影響;在這裡使用者可以根據查詢的模式和習慣,通過拖曳的方式調整各個維度在rowkeys上的順序。推薦的順序為:mandatory 維度、where 過濾條件**現頻率較多的維度、高基數維度、低基數維度。這樣做的好處是,充分利用過濾條件來縮小在 hbase 中掃瞄的範圍,從而提高查詢的效率。

指定 shardby 的列,明細資料將按照該列的值分片;沒有指定 shardby 的列,則預設將根據所有列中的資料進行分片;選擇適當的 shardby 列,可以使明細資料較為均勻的分散在多個資料片上,提高並行性,進而獲得更理想的查詢效率;建議選擇基數較大的列作為 shardby 列,以避免資料分散不均勻

參考:1、

2、3、

建立Oracle的DB Link實戰

當有在一台資料庫伺服器上集合或者分類篩選位於其他資料庫伺服器上的資料時,如果從應用層面上來解決問題,可能需要占用大量記憶體並且很費事。oracle資料庫本身提供了db link的機制來達到這個目的,以下以具體步驟來實現這個操作。1.首先在管理資料庫上建立到乙個資料庫的db link.drop exi...

一次效能調優的實戰

專案情況 是乙個大型公司的內部辦公系統,該系統有兩個和一般企業應用不太一樣的特點 一是使用者量非常多,人員數達到2w左右,另乙個是採用分級管理的形式,各個分公司資料分開管理。我們的定位 我們是作為業務平台的提供商參與這個專案的,我們提供底層的開發平台,系統整合商在此基礎上進行二次開發。在專案從開發到...

一次效能調優的實戰

專案情況 是乙個大型公司的內部辦公系統,該系統有兩個和一般企業應用不太一樣的特點 一是使用者量非常多,人員數達到2w左右,另乙個是採用分級管理的形式,各個分公司資料分開管理。我們的定位 我們是作為業務平台的提供商參與這個專案的,我們提供底層的開發平台,系統整合商在此基礎上進行二次開發。在專案從開發到...