Doris【數據模型】

一、數據模型簡介

在 Doris 中,數據以表(Table)的形式進行邏輯上的描述。 一張表包括行(Row)和列(Column)。Row 即用戶的一行數據。Column 用于描述一行數據中不同的字段。

Column 可以分為兩大類:Key 和 Value。從業務角度看,Key 和 Value 可以分別對應維度列和指標列。Doris的key列是建表語句中指定的列,建表語句中的關鍵字'unique key'或'aggregate key'或'duplicate key'后面的列就是 Key 列,除了 Key 列剩下的就是 Value 列。

Doris 的數據模型主要分為3類:

  • Aggregate
  • Unique
  • Duplicate

下面我們分別介紹。

二、明細模型【Duplicate】

建表

CREATE TABLE order_info (order_date date NOT NULL COMMENT '下單日期',order_id int(11) NOT NULL COMMENT '訂單id',buy_num tinyint(4) NULL COMMENT '購買件數',user_id int(11) NULL COMMENT '[-1223371, 1223371]',create_time datetime NULL COMMENT '創建時間',update_time datetime NULL COMMENT '更新時間'
) ENGINE=OLAP
DUPLICATE KEY(order_date, order_id)
COMMENT 'OLAP'
DISTRIBUTED BY HASH(order_id) BUCKETS 2
PROPERTIES (
"replication_allocation" = "tag.location.default: 1"
);

通過Flink Sql自帶的datagen生成測試數據:

CREATE TABLE order_info_source (order_date DATE,order_id     INT,buy_num      INT,user_id      INT,create_time  TIMESTAMP(3),update_time   TIMESTAMP(3)
) WITH ('connector' = 'datagen','rows-per-second' =  '10','fields.order_id.min' = '99999','fields.order_id.max' = '10001','fields.user_id.min' = '10001','fields.user_id.max' = '90001','fields.buy_num.min' = '1','fields.buy_num.max' = '200','number-of-rows' = '10000'
)

datagen參數

'rows-per-second' = '1000' : 每秒發送1000條數據
'fields.order_id.min' = '99999': order_id最小值為99999
'fields.order_id.max' = '10001': order_id最大值為10001
'fields.user_id.min' = '10001': user_id最小值為10001
'fields.user_id.max' = '90001': user_id最大值為90001
'fields.buy_num.min' = '1': buy_num最小值為1
'fields.buy_num.max' = '200': buy_num最大值為200
'number-of-rows' = '10000': 共發送10000條數據, 不設置的話會無限量發送數據

參考文檔:DataGen | Apache FlinkDataGen SQL Connector # Scan Source: Bounded Scan Source: UnBoundedThe DataGen connector allows for creating tables based on in-memory data generation. This is useful when developing queries locally without access to external systems such as Kafka. Tables can include Computed Column syntax which allows for flexible record generation.The DataGen connector is built-in, no additional dependencies are required.Usage # By default, a DataGen table will create an unbounded number of rows with a random value for each column.icon-default.png?t=N7T8https://nightlies.apache.org/flink/flink-docs-release-1.15/docs/connectors/table/datagen/

注冊Sink 表

CREATE TABLE order_info_sink (  
order_date DATE,  
order_id INT,  
buy_num INT,
user_id INT,
create_time TIMESTAMP(3),
update_time TIMESTAMP(3)
)  
WITH (
'connector' = 'doris',   
'fenodes' = '192.168.56.XXX:8030',   
'table.identifier' = 'test.order_info_example',   
'username' = 'test123',   
'password' = 'passwd123',   
'sink.label-prefix' = 'sink_doris_label_8'
)

寫入Sink 表

insert into order_info_sink select * from order_info_source

通過mysql客戶端查看Doris Sink表數據?

mysql> select * from  test.order_info_example limit 10;
+------------+----------+---------+---------+---------------------+---------------------+
| order_date | order_id | buy_num | user_id | create_time         | update_time         |
+------------+----------+---------+---------+---------------------+---------------------+
| 2024-02-22 |    30007 |      10 |   10560 | 2024-02-22 07:42:21 | 2024-02-22 07:42:21 |
| 2024-02-22 |    30125 |      16 |   17591 | 2024-02-22 07:42:26 | 2024-02-22 07:42:26 |
| 2024-02-22 |    30176 |      17 |   10871 | 2024-02-22 07:42:24 | 2024-02-22 07:42:24 |
| 2024-02-22 |    30479 |      16 |   19847 | 2024-02-22 07:42:25 | 2024-02-22 07:42:25 |
| 2024-02-22 |    30128 |      16 |   19807 | 2024-02-22 07:42:24 | 2024-02-22 07:42:24 |
| 2024-02-22 |    30039 |      13 |   18237 | 2024-02-22 07:42:28 | 2024-02-22 07:42:28 |
| 2024-02-22 |    30060 |      10 |   18309 | 2024-02-22 07:42:24 | 2024-02-22 07:42:24 |
| 2024-02-22 |    30246 |      18 |   10855 | 2024-02-22 07:42:24 | 2024-02-22 07:42:24 |
| 2024-02-22 |    30288 |      19 |   12347 | 2024-02-22 07:42:26 | 2024-02-22 07:42:26 |
| 2024-02-22 |    30449 |      17 |   11488 | 2024-02-22 07:42:23 | 2024-02-22 07:42:23 |
+------------+----------+---------+---------+---------------------+---------------------+
10 rows in set (0.05 sec)

三、Unique模型

當用戶有數據更新需求時,可以選擇使用Unique數據模型。Unique模型能夠保證Key的唯一性,當用戶更新一條數據時,新寫入的數據會覆蓋具有相同key的舊數據。

Unique模型提供了兩種實現方式:

  • 讀時合并(merge-on-read)。在讀時合并實現中,用戶在進行數據寫入時不會觸發任何數據去重相關的操作,所有數據去重的操作都在查詢或者compaction時進行。因此,讀時合并的寫入性能較好,查詢性能較差,同時內存消耗也較高。
  • 寫時合并(merge-on-write)。在1.2版本中,我們引入了寫時合并實現,該實現會在數據寫入階段完成所有數據去重的工作,因此能夠提供非常好的查詢性能。

Unique建表

CREATE TABLE IF NOT EXISTS example_db.example_tbl_unique
(`user_id` LARGEINT NOT NULL COMMENT "用戶id",`username` VARCHAR(50) NOT NULL COMMENT "用戶昵稱",`city` VARCHAR(20) COMMENT "用戶所在城市",`age` SMALLINT COMMENT "用戶年齡",`sex` TINYINT COMMENT "用戶性別",`phone` LARGEINT COMMENT "用戶電話",`address` VARCHAR(500) COMMENT "用戶地址",`register_time` DATETIME COMMENT "用戶注冊時間"
)
UNIQUE KEY(`user_id`, `username`)
DISTRIBUTED BY HASH(`user_id`) BUCKETS 1
PROPERTIES (
"replication_allocation" = "tag.location.default: 1"
);

?這是一個典型的用戶基礎信息表。這類數據沒有聚合需求,只需保證主鍵唯一性。(這里的主鍵為 user_id + username)。

寫時合并

CREATE TABLE IF NOT EXISTS example_db.example_tbl_unique_merge_on_write
(`user_id` LARGEINT NOT NULL COMMENT "用戶id",`username` VARCHAR(50) NOT NULL COMMENT "用戶昵稱",`city` VARCHAR(20) COMMENT "用戶所在城市",`age` SMALLINT COMMENT "用戶年齡",`sex` TINYINT COMMENT "用戶性別",`phone` LARGEINT COMMENT "用戶電話",`address` VARCHAR(500) COMMENT "用戶地址",`register_time` DATETIME COMMENT "用戶注冊時間"
)
UNIQUE KEY(`user_id`, `username`)
DISTRIBUTED BY HASH(`user_id`) BUCKETS 1
PROPERTIES (
"replication_allocation" = "tag.location.default: 1",
"enable_unique_key_merge_on_write" = "true"
);

【注意】

  1. Unique表的實現方式只能在建表時確定,無法通過schema change進行修改。
  2. 舊的Merge-on-read的實現無法無縫升級到Merge-on-write的實現(數據組織方式完全不同),如果需要改為使用寫時合并的實現版本,需要手動執行insert into unique-mow-table select * from source table.

四、聚合模型【Aggregate】?

CREATE DATABASE IF NOT EXISTS example_db;CREATE TABLE IF NOT EXISTS example_db.example_tbl_agg1
(`user_id` LARGEINT NOT NULL COMMENT "用戶id",`date` DATE NOT NULL COMMENT "數據灌入日期時間",`city` VARCHAR(20) COMMENT "用戶所在城市",`age` SMALLINT COMMENT "用戶年齡",`sex` TINYINT COMMENT "用戶性別",`last_visit_date` DATETIME REPLACE DEFAULT "1970-01-01 00:00:00" COMMENT "用戶最后一次訪問時間",`cost` BIGINT SUM DEFAULT "0" COMMENT "用戶總消費",`max_dwell_time` INT MAX DEFAULT "0" COMMENT "用戶最大停留時間",`min_dwell_time` INT MIN DEFAULT "99999" COMMENT "用戶最小停留時間"
)
AGGREGATE KEY(`user_id`, `date`, `city`, `age`, `sex`)
DISTRIBUTED BY HASH(`user_id`) BUCKETS 1
PROPERTIES (
"replication_allocation" = "tag.location.default: 1"
);

表中的列按照是否設置了?AggregationType,分為 Key (維度列) 和 Value(指標列)。沒有設置?AggregationType?的,如?user_iddateage?... 等稱為?Key,而設置了?AggregationType?的稱為?Value

當我們導入數據時,對于 Key 列相同的行會聚合成一行,而 Value 列會按照設置的?AggregationType?進行聚合。?AggregationType?目前有以下幾種聚合方式和agg_state:

  1. SUM:求和,多行的 Value 進行累加。
  2. REPLACE:替代,下一批數據中的 Value 會替換之前導入過的行中的 Value。
  3. MAX:保留最大值。
  4. MIN:保留最小值。
  5. REPLACE_IF_NOT_NULL:非空值替換。和 REPLACE 的區別在于對于null值,不做替換。
  6. HLL_UNION:HLL 類型的列的聚合方式,通過 HyperLogLog 算法聚合。
  7. BITMAP_UNION:BIMTAP 類型的列的聚合方式,進行位圖的并集聚合。

數據導入

insert into example_db.example_tbl_agg1 values
(10000,"2017-10-01","北京",20,0,"2017-10-01 06:00:00",20,10,10),
(10000,"2017-10-01","北京",20,0,"2017-10-01 07:00:00",15,2,2),
(10001,"2017-10-01","北京",30,1,"2017-10-01 17:05:45",2,22,22),
(10002,"2017-10-02","上海",20,1,"2017-10-02 12:59:12",200,5,5),
(10003,"2017-10-02","廣州",32,0,"2017-10-02 11:20:00",30,11,11),
(10004,"2017-10-01","深圳",35,0,"2017-10-01 10:00:15",100,3,3),
(10004,"2017-10-03","深圳",35,0,"2017-10-03 10:20:22",11,6,6);

?查詢數據

?五、數據模型的選擇建議

因為數據模型在建表時就已經u企鵝人,且無法修改。所以,選擇一個何時的數據模型非常重要。

  1. Aggregate模型可以通過預聚合,極大的降低聚合查詢時所需掃描的數據量和查詢的計算量,非常適合有固定模式的報表查詢場景。但是該模型對count(*)查詢不是很友好。同時因為固定了Value列上的聚合方式,在進行其他類型的聚合查詢時,需要考慮語意正確性。
  2. Unique模型針對需要唯一主鍵約束的場景,可以保證主鍵唯一性約束。但是無法利用RollUp等預聚合帶來的查詢優勢。對于聚合查詢有較高性能需求的用戶,推薦使用1.2版本加入的寫時合并實現。
  3. Duplicate適合任意維度的ad-hoc查詢。雖然同樣無法利用預聚合的特性,但是不受聚合模型的約束,可以發揮列存模型的優勢(只讀取相關列,而不需要讀取所有的列)。

本文來自互聯網用戶投稿,該文觀點僅代表作者本人,不代表本站立場。本站僅提供信息存儲空間服務,不擁有所有權,不承擔相關法律責任。
如若轉載,請注明出處:http://www.pswp.cn/news/713871.shtml
繁體地址,請注明出處:http://hk.pswp.cn/news/713871.shtml
英文地址,請注明出處:http://en.pswp.cn/news/713871.shtml

如若內容造成侵權/違法違規/事實不符,請聯系多彩編程網進行投訴反饋email:809451989@qq.com,一經查實,立即刪除!

相關文章

autoware.universe中跟蹤模塊詳解,一看就懂!

目錄 問題:閱讀關鍵點:總結問題: 根據對預測模塊代碼的分析,發現預測框出現在點云前方的原因在于跟蹤框出現在點云前方 對rviz上的目標進行觀察后發現 車輛的檢測框先出來一段時間后,跟蹤框和預測框同步一塊出來 跟蹤框總是超出點云一部分 閱讀關鍵點: 每個跟蹤器最少要統計…

7.1.2 Selenium的用法1

目錄 1. 初始化瀏覽器對象和訪問頁面 2. 查找節點及節點交互 2.1 查找單個節點 (1)獲取方法1——特定方法 (2)通用方法 2.2 查找多個節點 2.3 節點交互 3. 動作鏈 4. 執行 JavaScript 之下拉進度條 5. 獲取節點信息 5.…

谷歌seo推廣秒收錄怎么做?

谷歌SEO推廣秒收錄想要做到,可以利用我們光算科技獨家技術,GSI快速收錄,通過技術手段和操作,幫你的網站快速被谷歌發現和記錄 這項技術具體核心就是GPC爬蟲池系統,這個系統是專門研究谷歌搜索引擎優化的規律和算法創造…

【QT】QTableView或QTableWidget 搭配QLineEdit實現數據的搜索顯示

在 Qt 中,QTableView 和 QTableWidget 都可以用來實現數據的搜索和顯示,但它們的適用場景和實現方式有所不同: QTableView 適用場景:QTableView 適用于更復雜的場景,尤其是當需要處理大量數據或需要高度定制化的表格時…

66-ES6:var,let,const,函數的聲明方式,函數參數,剩余函數,延展操作符,嚴格模式

1.JavaScript語言的執行流程 編譯階段:構建執行函數;執行階段:代碼依次執行 2.代碼塊:{ } 3.變量聲明方式var 有聲明提升,允許重復聲明,聲明函數級作用域 訪問:聲明后訪問都是正常的&…

拿下邊界機器進行內網滲透的方案

拿下機器后,使用代理訪問內網 windows環境:reGeorg與proxifier Linux環境:reGeorg與proxychains, 使用nmap等工具進行掃描,發現web服務的主機和其它信息。有時這些邊界機器上會記錄一些 內網服務器上的一些信息&…

QT C++實現點擊按鍵彈出窗口并顯示圖片/視頻|多窗口應用程序的設計和開發

一、介紹 首先,QT界面開發中主要大體分為2種多窗口的形式: 嵌入式: 新生成的窗口嵌入在主窗口內部獨立窗口: 以彈窗形式的新窗口生成和展示 這里就講解最簡單的:點擊案件后,跳出一個新窗口 二、代碼實…

利用FFMPEG 將RTSP流的音頻G711 轉碼為AAC 并 推流到RTMP

之前我們的視頻轉碼項目中 是沒有加入音頻的 現在 需要加入音頻 ,由于RTMP只支持AAC的 音頻流 而有的RTSP流的音頻編碼并不是AAC 大多數都是G711編碼 還分為G711A 和G711U 之前用ffmpeg命令行可以直接 完成轉碼 并推送到RTMP 但是考慮到無法獲取更詳細的狀…

Qt篇——QTableWidget保存表格數據到Excel文件中,讀Excel內容到QTableWidget

表格和excel例子如下圖所示&#xff1a; 一、QTableWidget保存表格數據到Excel文件中 代碼如下&#xff1a; &#xff08;pro文件中添加QT axcontainer&#xff09; #include <QAxObject>void MainWindow::saveTableToExcel() {QDateTime current_date_time QDateTi…

六、MQTT源碼簡單瀏覽

1、MQTT程序分層 1.1、MQTT客戶端工作流程 (1)連接MQTT服務器。 (2)客戶端向服務器發送訂閱主題。 (3)客戶端等待MQTT的消息。 (4)客戶端向服務器發送消息。 2.2、MQTT程序結構 APP層 while循環或一個進程中&#xff1a;等待消息&#xff0c;處理消息&#xff1b; 發送消…

[法規規劃|方案實操]數據資產入表,城投將獲融資新渠道

2023年8月&#xff0c;財政部發布了《企業數據資源相關會計處理暫行規定》&#xff0c;并從2024年1月1日開始實施&#xff0c;標志著數據資產正式納入企業的資產負債表。這一舉措被視為數據資產從理論走向實踐的重大一步。 數據資產入表對城投運營模式的影響 隨著全球經濟格局…

Vue3速成

文章目錄 day 11. 創建vue3工程3. 響應式數據4. 計算屬性 day 25. watch 監視6. watchEffect7. 標簽的ref屬性8. 回顧TS中的接口_泛型_自定義類型 day 1 1. 創建vue3工程 相關代碼如下&#xff1a; ## 創建vue工程 npm create vuelastest## 安裝node_modules npm install //…

JSON 文件里的 “$schema” 是干什么用的?

最近我在做一些前端項目&#xff0c;我發現有的配置文件&#xff0c;比如 .prettierrc.json 或者 tsconfig.json 里面都會看到一個 $schema 字段&#xff0c;有點好奇&#xff0c;就查了一下。 什么是 JSON Schema JSON Schema是一種基于JSON (JavaScript Object Notation) 的…

【Leetcode】2369. 檢查數組是否存在有效劃分

文章目錄 題目思路代碼結果 題目 題目鏈接 給你一個下標從 0 開始的整數數組 nums &#xff0c;你必須將數組劃分為一個或多個 連續 子數組。 如果獲得的這些子數組中每個都能滿足下述條件 之一 &#xff0c;則可以稱其為數組的一種 有效 劃分&#xff1a; 子數組 恰 由 2 個…

MATLAB算法實戰應用案例精講-【圖像處理】三維重建(最終篇)

目錄 前言 相機定標和三維重建 針孔相機模型和變形 三維成像 一、機器視覺系統組成

大數據智能化-長視頻領域

隨著數字化時代的到來&#xff0c;長視頻領域的發展迎來了新的機遇和挑戰。在這一背景下&#xff0c;大數據智能化技術的應用成為長視頻行業提升用戶體驗、優化運營管理的重要手段之一。本文將從優愛騰3大長視頻背景需求出發&#xff0c;分析靜態資源CDN、視頻文件存儲與分發、…

網絡安全、信息安全、計算機安全,有何區別?

這三個概念都存在&#xff0c;一般人可能會混為一談。 究竟它們之間是什么關系&#xff1f;并列&#xff1f;交叉&#xff1f; 可能從廣義上來說它們都可以用來表示安全security這樣一個籠統的概念。 但如果從狹義上理解&#xff0c;它們應該是有區別的&#xff0c;區別在哪呢&…

力扣hot100題解(python版36-40題)

36、二叉樹的中序遍歷 給定一個二叉樹的根節點 root &#xff0c;返回 它的 *中序 遍歷* 。 示例 1&#xff1a; 輸入&#xff1a;root [1,null,2,3] 輸出&#xff1a;[1,3,2]示例 2&#xff1a; 輸入&#xff1a;root [] 輸出&#xff1a;[]示例 3&#xff1a; 輸入&am…

tcping實用小工具

Tcping實用小工具命令詳解 一、tcping介紹 tcping&#xff1a;tcping命令基于tcp協議監控&#xff0c;可以從較低級別的協議獲得簡單的&#xff0c;可能不可靠的數據報服務。 原則上&#xff0c;TCP應該能夠在從容硬線連接到分組交換或電路交換網絡的各種通信系統之上操作。 …

【機器學習基礎】層次聚類-BIRCH聚類

&#x1f680;個人主頁&#xff1a;為夢而生~ 關注我一起學習吧&#xff01; &#x1f4a1;專欄&#xff1a;機器學習 歡迎訂閱&#xff01;相對完整的機器學習基礎教學&#xff01; ?特別提醒&#xff1a;針對機器學習&#xff0c;特別開始專欄&#xff1a;機器學習python實戰…