文章目錄
MergeTree系清單引擎之SummingMergeTree
一、SummingMergeTree基本講解
二、使用SummingMergeTree注意以下幾點
三、測試執行個體
1、測試不指定聚合字段同時測試不同分區内,相同排序key資料不會被合并
2、測試指定一個聚合字段
3、測試指定多個聚合字段
MergeTree系清單引擎之SummingMergeTree
一、SummingMergeTree基本講解
該引擎繼承了MergeTree引擎,當合并 SummingMergeTree 表的資料片段時,ClickHouse 會把所有具有相同主鍵的行合并為一行,該行包含了被合并的行中具有數值資料類型的列的彙總值,即如果存在重複的資料,會對對這些重複的資料進行合并成一條資料,類似于group by的效果,可以顯著減少存儲空間并加快資料查詢速度。
如果使用者隻需要查詢資料的彙總結果,不關心明細資料,并且資料的彙總條件是預先明确的,即GROUP BY的分組字段是确定的,可以使用該表引擎。
- SummingMergeTree建表語句:
CREATE TABLE [IF NOT EXISTS] [db.]table_name [ON CLUSTER cluster]
(
name1 [type1] [DEFAULT|MATERIALIZED|ALIAS expr1],
name2 [type2] [DEFAULT|MATERIALIZED|ALIAS expr2],
...
) ENGINE = SummingMergeTree([columns])
[PARTITION BY expr]
[ORDER BY expr]
[SAMPLE BY expr]
[SETTINGS name=value, ...]
對以上建表語句的解釋如下:
[columns]: 将要被彙總的列,或者多個列,多個列需要寫在元組中。可選參數。所選的列必須是數值類型,并且不可位于主鍵中。如果沒有指定 [columns],ClickHouse 會把所有不在主鍵中的數值類型的列都進行彙總。
二、使用SummingMergeTree注意以下幾點
- SummingMergeTree是根據什麼對兩條資料進行合并的
用ORBER BY排序鍵作為聚合資料的條件Key。即如果排序key是相同的,則會合并成一條資料,并對指定的合并字段進行聚合。
- 僅對分區内的相同排序key的資料行進行合并
以資料分區為機關來聚合資料。當分區合并時,同一資料分區内聚合Key相同的資料會被合并彙總,而不同分區之間的資料則不會被彙總。
- 如果沒有指定聚合字段,會怎麼聚合
如果沒有指定聚合字段,則會按照非主鍵的數值類型字段進行聚合。
- 對于非彙總字段的資料,該保留哪一條
如果兩行資料除了排序字段相同,其他的非聚合字段不相同,那麼在聚合發生時,會保留最初的那條資料,新插入的資料對應的那個字段值會被舍棄。
三、測試執行個體
1、測試不指定聚合字段同時測試不同分區内,相同排序key資料不會被合并
#建立表 t_summing_mt ,使用SummingMergeTree表引擎
node1 :) create table t_summing_mt(
:-] id UInt8,
:-] name String,
:-] age UInt8,
:-] loc String,
:-] dept String,
:-] workdays UInt8,
:-] salary Decimal32(2)
:-] ) engine = SummingMergeTree()
:-] order by (id,age)
:-] primary key id
:-] partition by loc;
#向表 t_summing_mt 中插入以下資料
node1 :) insert into t_summing_mt values (1,'張三',18,'北京','大資料',24,10000),
:-] (2,'李四',19,'上海','java',22,8000),
:-] (3,'王五',20,'北京','java',26,12000);
#檢視表 t_summing_mt 中的資料
node1 :) select * from t_summing_mt;
┌─id─┬─name─┬─age─┬─loc──┬─dept───┬─workdays─┬───salary─┐
│ 1 │ 張三 │ 18 │ 北京 │ 大資料 │ 24 │ 10000.00 │
│ 3 │ 王五 │ 20 │ 北京 │ java │ 26 │ 12000.00 │
└────┴──────┴─────┴──────┴────────┴──────────┴──────────┘
┌─id─┬─name─┬─age─┬─loc──┬─dept─┬─workdays─┬──salary─┐
│ 2 │ 李四 │ 19 │ 上海 │ java │ 22 │ 8000.00 │
└────┴──────┴─────┴──────┴──────┴──────────┴─────────┘
#向表 t_summing_mt 中插入一條排序鍵相同的資料
node1 :) insert into t_summing_mt values (1,'馬六',18,'北京','前端',27,15000);
#檢視表 t_summing_mt中的資料
node1 :) select * from t_summing_mt;
┌─id─┬─name─┬─age─┬─loc──┬─dept───┬─workdays─┬───salary─┐
│ 1 │ 張三 │ 18 │ 北京 │ 大資料 │ 24 │ 10000.00 │
│ 3 │ 王五 │ 20 │ 北京 │ java │ 26 │ 12000.00 │
└────┴──────┴─────┴──────┴────────┴──────────┴──────────┘
┌─id─┬─name─┬─age─┬─loc──┬─dept─┬─workdays─┬───salary─┐
│ 1 │ 馬六 │ 18 │ 北京 │ 前端 │ 27 │ 15000.00 │
└────┴──────┴─────┴──────┴──────┴──────────┴──────────┘
┌─id─┬─name─┬─age─┬─loc──┬─dept─┬─workdays─┬──salary─┐
│ 2 │ 李四 │ 19 │ 上海 │ java │ 22 │ 8000.00 │
└────┴──────┴─────┴──────┴──────┴──────────┴─────────┘
#手動執行optimize 指令觸發合并相同分區資料
node1 :) optimize table t_summing_mt;
#檢視表 t_summing_mt 中的資料
node1 :) select * from t_summing_mt;
┌─id─┬─name─┬─age─┬─loc──┬─dept───┬─workdays─┬───salary─┐
│ 1 │ 張三 │ 18 │ 北京 │ 大資料 │ 51 │ 25000.00 │
│ 3 │ 王五 │ 20 │ 北京 │ java │ 26 │ 12000.00 │
└────┴──────┴─────┴──────┴────────┴──────────┴──────────┘
┌─id─┬─name─┬─age─┬─loc──┬─dept─┬─workdays─┬──salary─┐
│ 2 │ 李四 │ 19 │ 上海 │ java │ 22 │ 8000.00 │
└────┴──────┴─────┴──────┴──────┴──────────┴─────────┘
注意:我們可以看到當不指定 聚合字段時,有相同排序字段行進行聚合時,會将數值類型的字段進行聚合合并。
#繼續向表 t_summing_mt中插入以下資料:
node1 :) insert into t_summing_mt values (1,'張三',18,'南京','java',18,12000);
#檢視表 t_summing_mt中的資料
node1 :) select * from t_summing_mt;
┌─id─┬─name─┬─age─┬─loc──┬─dept─┬─workdays─┬───salary─┐
│ 1 │ 張三 │ 18 │ 南京 │ java │ 18 │ 12000.00 │
└────┴──────┴─────┴──────┴──────┴──────────┴──────────┘
┌─id─┬─name─┬─age─┬─loc──┬─dept───┬─workdays─┬───salary─┐
│ 1 │ 張三 │ 18 │ 北京 │ 大資料 │ 51 │ 25000.00 │
│ 3 │ 王五 │ 20 │ 北京 │ java │ 26 │ 12000.00 │
└────┴──────┴─────┴──────┴────────┴──────────┴──────────┘
┌─id─┬─name─┬─age─┬─loc──┬─dept─┬─workdays─┬──salary─┐
│ 2 │ 李四 │ 19 │ 上海 │ java │ 22 │ 8000.00 │
└────┴──────┴─────┴──────┴──────┴──────────┴─────────┘
#手動指定optimize 指令合并相同排序key的資料
node1 :) optimize table t_summing_mt;
#檢視表 t_summing_mt中的資料
node1 :) select * from t_summing_mt;
┌─id─┬─name─┬─age─┬─loc──┬─dept─┬─workdays─┬───salary─┐
│ 1 │ 張三 │ 18 │ 南京 │ java │ 18 │ 12000.00 │
└────┴──────┴─────┴──────┴──────┴──────────┴──────────┘
┌─id─┬─name─┬─age─┬─loc──┬─dept───┬─workdays─┬───salary─┐
│ 1 │ 張三 │ 18 │ 北京 │ 大資料 │ 51 │ 25000.00 │
│ 3 │ 王五 │ 20 │ 北京 │ java │ 26 │ 12000.00 │
└────┴──────┴─────┴──────┴────────┴──────────┴──────────┘
┌─id─┬─name─┬─age─┬─loc──┬─dept─┬─workdays─┬──salary─┐
│ 2 │ 李四 │ 19 │ 上海 │ java │ 22 │ 8000.00 │
└────┴──────┴─────┴──────┴──────┴──────────┴─────────┘
2、測試指定一個聚合字段
#删除表 t_summing_mt,重新建立表 t_summing_mt ,使用SummingMergeTree引擎
node1 :) create table t_summing_mt(
:-] id UInt8,
:-] name String,
:-] age UInt8,
:-] loc String,
:-] dept String,
:-] workdays UInt8,
:-] salary Decimal32(2)
:-] ) engine = SummingMergeTree(salary)
:-] order by (id,age)
:-] primary key id
:-] partition by loc;
#向表 t_summing_mt 中插入以下資料
node1 :) insert into t_summing_mt values (1,'張三',18,'北京','大資料',24,10000),
:-] (2,'李四',19,'上海','java',22,8000),
:-] (3,'王五',20,'北京','java',26,12000);
#檢視表 t_summing_mt 中的資料
node1 :) select * from t_summing_mt;
┌─id─┬─name─┬─age─┬─loc──┬─dept───┬─workdays─┬───salary─┐
│ 1 │ 張三 │ 18 │ 北京 │ 大資料 │ 24 │ 10000.00 │
│ 3 │ 王五 │ 20 │ 北京 │ java │ 26 │ 12000.00 │
└────┴──────┴─────┴──────┴────────┴──────────┴──────────┘
┌─id─┬─name─┬─age─┬─loc──┬─dept─┬─workdays─┬──salary─┐
│ 2 │ 李四 │ 19 │ 上海 │ java │ 22 │ 8000.00 │
└────┴──────┴─────┴──────┴──────┴──────────┴─────────┘
#向表 t_summing_mt 中插入一條排序鍵相同的資料
node1 :) insert into t_summing_mt values (1,'馬六',18,'北京','前端',27,15000);
#檢視表 t_summing_mt中的資料
node1 :) select * from t_summing_mt;
┌─id─┬─name─┬─age─┬─loc──┬─dept───┬─workdays─┬───salary─┐
│ 1 │ 張三 │ 18 │ 北京 │ 大資料 │ 24 │ 10000.00 │
│ 3 │ 王五 │ 20 │ 北京 │ java │ 26 │ 12000.00 │
└────┴──────┴─────┴──────┴────────┴──────────┴──────────┘
┌─id─┬─name─┬─age─┬─loc──┬─dept─┬─workdays─┬───salary─┐
│ 1 │ 馬六 │ 18 │ 北京 │ 前端 │ 27 │ 15000.00 │
└────┴──────┴─────┴──────┴──────┴──────────┴──────────┘
┌─id─┬─name─┬─age─┬─loc──┬─dept─┬─workdays─┬──salary─┐
│ 2 │ 李四 │ 19 │ 上海 │ java │ 22 │ 8000.00 │
└────┴──────┴─────┴──────┴──────┴──────────┴─────────┘
#手動執行optimize 指令觸發合并相同分區資料
node1 :) optimize table t_summing_mt;
#檢視表 t_summing_mt 中的資料
node1 :) select * from t_summing_mt;
┌─id─┬─name─┬─age─┬─loc──┬─dept───┬─workdays─┬───salary─┐
│ 1 │ 張三 │ 18 │ 北京 │ 大資料 │ 24 │ 25000.00 │
│ 3 │ 王五 │ 20 │ 北京 │ java │ 26 │ 12000.00 │
└────┴──────┴─────┴──────┴────────┴──────────┴──────────┘
┌─id─┬─name─┬─age─┬─loc──┬─dept─┬─workdays─┬──salary─┐
│ 2 │ 李四 │ 19 │ 上海 │ java │ 22 │ 8000.00 │
└────┴──────┴─────┴──────┴──────┴──────────┴─────────┘
3、測試指定多個聚合字段
#删除表 t_summing_mt,重新建立表 t_summing_mt ,使用SummingMergeTree引擎
node1 :) create table t_summing_mt(
:-] id UInt8,
:-] name String,
:-] age UInt8,
:-] loc String,
:-] dept String,
:-] workdays UInt8,
:-] salary Decimal32(2)
:-] ) engine = SummingMergeTree((salary,workdays))
:-] order by (id,age)
:-] primary key id
:-] partition by loc;
#向表 t_summing_mt 中插入以下資料
node1 :) insert into t_summing_mt values (1,'張三',18,'北京','大資料',24,10000),
:-] (2,'李四',19,'上海','java',22,8000),
:-] (3,'王五',20,'北京','java',26,12000);
#檢視表 t_summing_mt 中的資料
node1 :) select * from t_summing_mt;
┌─id─┬─name─┬─age─┬─loc──┬─dept───┬─workdays─┬───salary─┐
│ 1 │ 張三 │ 18 │ 北京 │ 大資料 │ 24 │ 10000.00 │
│ 3 │ 王五 │ 20 │ 北京 │ java │ 26 │ 12000.00 │
└────┴──────┴─────┴──────┴────────┴──────────┴──────────┘
┌─id─┬─name─┬─age─┬─loc──┬─dept─┬─workdays─┬──salary─┐
│ 2 │ 李四 │ 19 │ 上海 │ java │ 22 │ 8000.00 │
└────┴──────┴─────┴──────┴──────┴──────────┴─────────┘
#向表 t_summing_mt 中插入一條排序鍵相同的資料
node1 :) insert into t_summing_mt values (1,'馬六',18,'北京','前端',27,15000);
#檢視表 t_summing_mt中的資料
node1 :) select * from t_summing_mt;
┌─id─┬─name─┬─age─┬─loc──┬─dept───┬─workdays─┬───salary─┐
│ 1 │ 張三 │ 18 │ 北京 │ 大資料 │ 24 │ 10000.00 │
│ 3 │ 王五 │ 20 │ 北京 │ java │ 26 │ 12000.00 │
└────┴──────┴─────┴──────┴────────┴──────────┴──────────┘
┌─id─┬─name─┬─age─┬─loc──┬─dept─┬─workdays─┬───salary─┐
│ 1 │ 馬六 │ 18 │ 北京 │ 前端 │ 27 │ 15000.00 │
└────┴──────┴─────┴──────┴──────┴──────────┴──────────┘
┌─id─┬─name─┬─age─┬─loc──┬─dept─┬─workdays─┬──salary─┐
│ 2 │ 李四 │ 19 │ 上海 │ java │ 22 │ 8000.00 │
└────┴──────┴─────┴──────┴──────┴──────────┴─────────┘
#手動執行optimize 指令觸發合并相同分區資料
node1 :) optimize table t_summing_mt;
#檢視表 t_summing_mt 中的資料
node1 :) select * from t_summing_mt;
┌─id─┬─name─┬─age─┬─loc──┬─dept───┬─workdays─┬───salary─┐
│ 1 │ 張三 │ 18 │ 北京 │ 大資料 │ 51 │ 25000.00 │
│ 3 │ 王五 │ 20 │ 北京 │ java │ 26 │ 12000.00 │
└────┴──────┴─────┴──────┴────────┴──────────┴──────────┘
┌─id─┬─name─┬─age─┬─loc──┬─dept─┬─workdays─┬──salary─┐
│ 2 │ 李四 │ 19 │ 上海 │ java │ 22 │ 8000.00 │
└────┴──────┴─────┴──────┴──────┴──────────┴─────────┘
- 📢歡迎點贊 👍 收藏 ⭐留言 📝 如有錯誤敬請指正!
- 📢本文由 Lansonli 原創
- 📢停下休息的時候不要忘了别人還在奔跑,希望大家抓緊時間學習,全力奔赴更美好的生活✨