大數據SQL數據傾斜與數據膨脹的優化與經驗總結

来源:https://www.cnblogs.com/88223100/archive/2023/06/18/Optimization-and-experience-summary-of-Big-data-SQL-data-skew-and-data-expansion.html
-Advertisement-
Play Games

本文主要基於團隊實際開發經驗與積累,並結合了業界對大數據SQL的使用與優化,嘗試給出相對系統性的解決方案。 ...


本文主要基於團隊實際開發經驗與積累,並結合了業界對大數據SQL的使用與優化,嘗試給出相對系統性的解決方案。

背景

目前市面上大數據查詢分析引擎層出不窮,如Spark,Hive,Presto等,因其友好的SQL語法,被廣泛應用於各領域分析,公司內部也有優秀的ODPS SQL供用戶使用。
筆者所在團隊的項目也借用ODPS SQL去檢測業務中潛在的安全風險。在給業務方使用與答疑過程中,我們發現大多含有性能瓶頸的SQL,主要集中在數據傾斜與數據膨脹問題中。因此,本文主要基於團隊實際開發經驗與積累,並結合業界對大數據SQL的使用與優化,嘗試給出相對系統性的解決方案。
本文主要涉及業務SQL執行層面的優化,暫不涉及參數優化。若設置參數,首先確定執行層面哪個階段(Map/Reduce/Join)任務執行時間較長,從而設置對應參數。
本文主要分為以下三個部分:第一部分,會引入數據傾斜與數據膨脹問題。第二部分,介紹當數據傾斜與數據膨脹發生時,如何排查與定位。第三部分,會從系統層面給出常見優化思路。

問題篇

數據傾斜

數據傾斜是指在分散式計算時,大量相同的key被分發到同一個reduce節點中。針對某個key值的數據量比較多,會導致該節點的任務數據量遠大於其他節點的平均數據量,運行時間遠高於其他節點的平均運行時間,拖累了整體SQL執行時間。
其主要原因是key值分佈不均導致的Reduce處理數據不均勻。本文將從Map端優化,Reduce端優化和Join端優化三方面給出相應解決方案。

數據膨脹

數據膨脹是指任務的輸出條數/數據量級比輸入條數/數據量級大很多,如100M的數據作為任務輸入,最後輸出1T的數據。這種情況不僅運行效率會降低,部分任務節點在運行key值量級過大時,有可能發生資源不足或失敗情況。

排查定位篇

本節主要關註於業務SQL本身引起的長時間運行或者失敗,對於集群資源情況,平臺故障本身暫不考慮在內。
1.首先檢查輸入數據量級。與其他天相比有無明顯量級變化,是否因為數據量級的問題天然引起任務運行時間過長,如雙11,雙十二等大促節點。
2.觀察執行任務拆分後各個階段運行時間。與其他天相比有無明顯量級變化;在整個執行任務中時間耗時占比情況。
3.最耗時階段中,觀察各個Task的運行情況。Task列表中,觀察是否存在某幾個Task實例耗時明顯比平均耗時更長,是否存在某幾個Task實例處理輸入/輸出數據量級比平均數據量級消費產出更多。
4.根據步驟3中定位代碼行數,定位問題業務處理邏輯。

優化篇

數據傾斜

1. Map端優化

1.1 讀取數據合併

在數據源讀取查詢時,動態分區數過多可能造成小文件數過多,每個小文件至少都會作為一個塊啟動一個Map任務來完成。對於文件數量而言,等於 map數量 * 分區數。對於一個Map任務而言,其初始化的時間可能遠遠大於邏輯處理時間,因此通過調整Map參數把小文件合併成大文件進行處理,避免造成很大的資源浪費。

1.2 列裁剪

減少使用select * from table語句,過多選擇無用列會增加數據在集群上傳輸的IO開銷;
對於數據選擇,需要加上分區過濾條件進行篩選數據。

1.3 謂詞下推

在不影響結果的情況下,儘可能將過濾條件表達式靠近數據源位置,使之提前執行。通過在map端過濾減少數據輸出,降低集群IO傳輸,從而提升任務的性能。

1.4 數據重分佈

在Map階段做聚合時,使用隨機分佈函數distribute by rand(),控制Map端輸出結果的分發,即map端如何拆分數據給reduce端(預設hash演算法),打亂數據分佈,至少不會在Map端發生數據傾斜。

2. Reduce端優化

2.1 關聯key空值檢驗

部分實例發生長尾效應,很大程度上由於null值,空值導致,使得Reduce時含有臟值的數據被分發到同一臺機器中。
針對這種問題SQL,首先確認包含無效值的數據源表是否可以在Map階段直接過濾掉這些異常數據;如果後續SQL邏輯仍然需要這些數據,可以通過將空值轉變成隨機值,既不影響關聯也可以避免聚集。

SELECT  ta.id
FROM    ta
LEFT JOIN tb
ON      coalesce(ta.id , rand()) = tb.id;

2.2 排序優化

Order by為全局排序,當表數據量過大時,性能可能會出現瓶頸;Sort by為局部排序,確保Reduce任務內結果有序,全局排序不保證;Distribute by按照指定欄位進行Hash分片,把數據劃分到不同的Reducer中;CLUSTER BY:根據指定的欄位進行分桶,併在桶內進行排序,可以認為cluster by是distribute by+sort by。
對於排序而言,嘗試用distribute by+sort by確保reduce中結果有序,最後在全局有序。

-- 原始腳本
select *
from user_pay_table
where dt = '20221015'
order by amt
limit 500
;

-- 改進腳本
SELECT  *
FROM    user_pay_table
WHERE   dt = '20221015'
DISTRIBUTE BY ( CASE
                   WHEN amt < 100                  THEN 0
                   WHEN amt >= 100 AND age <= 2000 THEN 1
                   ELSE 2
                 END )
 SORT BY amt
LIMIT 500
;

3. Join端優化

3.1 大表join小表

通過將需要join的小表分發至map端記憶體中,將Join操作提前至map端執行,避免因分發key值不均勻引發的長尾效應,複雜度從(M*N)降至(M+N),從而提高執行效率。ODPS SQL與Hive SQL使用mapjoin,SPARK使用broadcast。

圖片

3.2 大表join大表

長尾效應由熱點數據導致,可以將熱點數據加入白名單中,通過對白名單數據和非白名單數據分別處理,再合併數據。

具體表現為打散傾斜key,進行兩端聚合(針對聚合)或者拆分傾斜key進行打散然後再合併數據。

數據膨脹

1. 避免笛卡爾積

Join關聯條件有誤,表Join進行笛卡爾積,造成數據量爆炸。

2. 關聯key區分度校驗

關註JoinKey區分度,key值區分度越低(distinct數量少),越有可能造成數據爆炸情況。如用戶下的性別列,交易下的省市列等。

3. 聚合操作誤用

部分聚合操作需要將中間結果記錄下來,最後再生成最終結果,這使得在select操作時,按照不同維度去重Distinct、不同維度開窗計算over Partition By可能會導致數據膨脹。針對這種業務邏輯,可以將一個SQL拆分成多個SQL分別進行處理操作。

總結

大數據SQL優化是一項涉及知識面較廣的工作,除了分析現有執行計劃之外,還需要學習相應查詢分析引擎設計原理。針對我們日常遇到的問題現總結分享給大家,供大家查閱。

參考資料:

ODPS SELECT語法:https://help.aliyun.com/document_detail/73777.html?utm_content=g_1000230851&spm=5176.20966629.toubu.3.f2991ddcpxxvD1#section-ag9-2c4-t0e
Presto Query Lifecycle:https://varada.io/blog/presto/accelerate-presto-trino-queries-data-lake/
A Definitive Guide To Hive Performance Tuning- 10 Excellent Tips:https://www.hdfstutorial.com/blog/hive-performance-tuning/
Presto Performance: Speed, Optimization & Tuning:https://ahana.io/learn/presto-performance/
Hive Optimizing Joins:https://docs.cloudera.com/HDPDocuments/HDP2/HDP-2.0.0.2/ds_Hive/optimize-joins.html
作者|霖玉

本文來自博客園,作者:古道輕風,轉載請註明原文鏈接:https://www.cnblogs.com/88223100/p/Optimization-and-experience-summary-of-Big-data-SQL-data-skew-and-data-expansion.html


您的分享是我們最大的動力!

-Advertisement-
Play Games
更多相關文章
  • 經過前幾篇文章的講解,初步瞭解ASP.NET Core MVC項目創建,啟動運行,以及命名約定,創建控制器,視圖,模型,接收參數,傳遞數據ViewData,ViewBag,路由,頁面佈局,wwwroot和客戶端庫,Razor語法,EnityFrameworkCore與資料庫,HttpContext,... ...
  • # 個人博客文章歸檔實現📑 # 前言 隨著博客的文章越來越多,那麼歸檔就顯得尤為重要,然後最近也是沒什麼課,加緊更新一下博客,之前也是更新了評論、留言板。 然後博客是使用的前後的不分離的項目,數據返回一般都是用的.NET的強類型數據返回,也會用到分佈視圖。 重點是一段sql查詢困惱我許久,在後端接 ...
  • 大家好,我是 god23bin。歡迎來到《一分鐘學一個 Linux 命令》系列,每天只需一分鐘,記住一個 Linux 命令不成問題。今天要說的是 ps 命令。 ...
  • MySQL作為一個流行的開源關係型資料庫管理系統,它可以運行在多種平臺上,支持多種存儲引擎,提供了靈活的數據操作和管理功能。 ...
  • Mysql8社區版日誌審計插件 過去從Mysql官方自帶general.log日誌的相比其他插件性能是最差的,我們考慮參考行業中較好的插件是MariaDB Audit Plugin, 可惜並不相容mysql 5.7與mysql 8.0以上版本。亞馬遜RDS for MySQL的開發團隊已經folk了 ...
  • ## 1.maven引入相關依賴 ~~~xml org.springframework.boot spring-boot-starter-data-redis org.apache.commons commons-pool2 2.11.1 com.fasterxml.jackson.core jac ...
  • 近日,極限數據 (北京) 科技有限公司(以下簡稱:極限科技)旗下的軟體 INFINI Easysearch 搜索引擎軟體 V1.0 通過統信 UOS 伺服器操作系統 V20 認證。 此次相容適配基於統信 UOS 伺服器操作系統 V20,聯合國產 CPU:海光 5000、海光 7000、兆芯 KH-3 ...
  • [TOC](MySQL主鍵、唯一索引、聯合索引的區別和作用) # 0. 簡介 索引是一類特殊的`文件`,用來存儲檢索信息,使資料庫查找更加快速。 # 1. 主鍵 主鍵是一類特殊的唯一索引,選擇某一列元素作為主鍵,用來表示每一行元素的特殊性,其特點如下 - 在一個數據表中只有一個主鍵; - 主鍵不能為 ...
一周排行
    -Advertisement-
    Play Games
  • 移動開發(一):使用.NET MAUI開發第一個安卓APP 對於工作多年的C#程式員來說,近來想嘗試開發一款安卓APP,考慮了很久最終選擇使用.NET MAUI這個微軟官方的框架來嘗試體驗開發安卓APP,畢竟是使用Visual Studio開發工具,使用起來也比較的順手,結合微軟官方的教程進行了安卓 ...
  • 前言 QuestPDF 是一個開源 .NET 庫,用於生成 PDF 文檔。使用了C# Fluent API方式可簡化開發、減少錯誤並提高工作效率。利用它可以輕鬆生成 PDF 報告、發票、導出文件等。 項目介紹 QuestPDF 是一個革命性的開源 .NET 庫,它徹底改變了我們生成 PDF 文檔的方 ...
  • 項目地址 項目後端地址: https://github.com/ZyPLJ/ZYTteeHole 項目前端頁面地址: ZyPLJ/TreeHoleVue (github.com) https://github.com/ZyPLJ/TreeHoleVue 目前項目測試訪問地址: http://tree ...
  • 話不多說,直接開乾 一.下載 1.官方鏈接下載: https://www.microsoft.com/zh-cn/sql-server/sql-server-downloads 2.在下載目錄中找到下麵這個小的安裝包 SQL2022-SSEI-Dev.exe,運行開始下載SQL server; 二. ...
  • 前言 隨著物聯網(IoT)技術的迅猛發展,MQTT(消息隊列遙測傳輸)協議憑藉其輕量級和高效性,已成為眾多物聯網應用的首選通信標準。 MQTTnet 作為一個高性能的 .NET 開源庫,為 .NET 平臺上的 MQTT 客戶端與伺服器開發提供了強大的支持。 本文將全面介紹 MQTTnet 的核心功能 ...
  • Serilog支持多種接收器用於日誌存儲,增強器用於添加屬性,LogContext管理動態屬性,支持多種輸出格式包括純文本、JSON及ExpressionTemplate。還提供了自定義格式化選項,適用於不同需求。 ...
  • 目錄簡介獲取 HTML 文檔解析 HTML 文檔測試參考文章 簡介 動態內容網站使用 JavaScript 腳本動態檢索和渲染數據,爬取信息時需要模擬瀏覽器行為,否則獲取到的源碼基本是空的。 本文使用的爬取步驟如下: 使用 Selenium 獲取渲染後的 HTML 文檔 使用 HtmlAgility ...
  • 1.前言 什麼是熱更新 游戲或者軟體更新時,無需重新下載客戶端進行安裝,而是在應用程式啟動的情況下,在內部進行資源或者代碼更新 Unity目前常用熱更新解決方案 HybridCLR,Xlua,ILRuntime等 Unity目前常用資源管理解決方案 AssetBundles,Addressable, ...
  • 本文章主要是在C# ASP.NET Core Web API框架實現向手機發送驗證碼簡訊功能。這裡我選擇是一個互億無線簡訊驗證碼平臺,其實像阿裡雲,騰訊雲上面也可以。 首先我們先去 互億無線 https://www.ihuyi.com/api/sms.html 去註冊一個賬號 註冊完成賬號後,它會送 ...
  • 通過以下方式可以高效,並保證數據同步的可靠性 1.API設計 使用RESTful設計,確保API端點明確,並使用適當的HTTP方法(如POST用於創建,PUT用於更新)。 設計清晰的請求和響應模型,以確保客戶端能夠理解預期格式。 2.數據驗證 在伺服器端進行嚴格的數據驗證,確保接收到的數據符合預期格 ...