首頁
編程語言
C語言|JAVA編程
Python編程
網頁編程
ASP編程|PHP編程
JSP編程
數據庫
MYSQL數據庫|SqlServer數據庫
Oracle數據庫|DB2數據庫
您现在的位置: 程式碼之家 >> 數據庫知識 >  >> DB2 資料庫 >> DB2 教學

DB2 SQL 極致效能調優:從游標重構到謂詞改寫的實戰技法

     編輯:DB2 教學

效能調優的核心邏輯

DB2 可擴展性仰賴「小而優化的 SQL + 精準的存取路徑 + 適配負載的緩衝池與儲存」。硬體升級只能暫緩瓶頸,SQL 層面的架構優化才是根本。當資料量與併發上升,原本在輕量負載下運作良好的「巢狀游標、大量子查詢、SELECT *」將成為災難。

經典案例:7 層游標合併為單一連接

問題代碼

批次程式在 7 個巢狀游標中逐層讀取 7 張表,並在應用層以程式邏輯做連接。首次上線跑 10 個小時仍未完成。

第一步:SQL 重構為單一連接

SELECT COL1, COL2, ... 
FROM ADDR A, NAME N, T3, T4, T5, T6, T7
WHERE A.COL1 = N.COL9
  AND N.COL9 = T3.COL3
  AND T3.COL3 = T4.COL4
  AND T4.COL4 <> T5.COL5
  AND T4.COLX <> T5.COLY
  AND T5.COL6 = T6.COL6
  AND T6.COL6 = T7.COL7
  AND T6.CODE = :hv

執行時間從 10+ 小時降至 4 分鐘。

第二步:EXPLAIN 發現優化器選擇錯誤連接順序

優化器以兩張龐大表(ADDR、NAME,各 5 億列)為外層驅動,導致嵌套循環連接極度膨脹。原因在於 <> 不等值連接條件,統計資訊無法準確估算選擇率。

四層次調優技術體系

層次 技術 適用場景 本案例效果
Package 級 REOPT(ONCE/ALWAYS/AUTO) 非均勻分布、主機變數高變動 批次僅單一謂詞 + 基數 1,開銷可忽略,但非最佳解
Statement 級 OPTIMIZE FOR n ROWS / FETCH FIRST n ROWS ONLY 僅需前 N 筆結果 批次需全量結果,不適用
Predicate 級 假過濾器 TX.CX=TX.CX / 空操作 +0, *1, CONCAT '' 調整過濾因子、改變連接順序 多重嘗試無效,LUW 優化器忽略空操作
終極重寫 SELECT DISTINCT 表表達式 / 跨查詢塊優化 強制指定查詢塊執行順序 生效,再降至 2 分鐘

終極技法:DISTINCT 表表達式強制連接順序

將小表優先連接、過濾後再與大表連接:

SELECT All columns needed
FROM ADDR, NAME,
     (SELECT DISTINCT columns
      FROM T3, T4, T5, T6, T7
      WHERE join conditions T3 through T7
        AND T6.CODE = :hv) AS TEMP
WHERE join conditions for ADDR, NAME and TEMP
  • DISTINCT 關鍵:強制優化器先實例化子查詢結果(唯一化並排序),再與外層大表連接。
  • 若省略 DISTINCT,優化器會合併查詢塊,退回原始連接順序。
  • 臨時結果僅數千列,排序開銷極低,換來連接順序最佳化,總耗時 2 分鐘。

進階:跨查詢塊優化(全域優化)

DB2 9 起引入 Global Query Optimization,優化器在 Query Rewrite (QWR) 階段自動嘗試跨查詢塊重寫。未來版本將更完善,但現階段仍需開發者掌握手動重寫技法,確保關鍵路徑受控。

實戰檢核清單

  1. 統計資訊最新:RUNSTATS 含分佈統計,確保優化器擁有精準全景。
  2. 避免應用層連接:盡可能在單一 SQL 完成多表連接。
  3. 善用 EXPLAIN:檢視存取路徑、連接順序、索引使用情況。
  4. 分層嘗試調優:Package → Statement → Predicate → 終極重寫,由輕入重。
  5. 謹慎使用終極技法:DISTINCT 表表達式可能由好變壞,上線前必須完整回歸測試。

掌握從結構重構到優化器導引的完整技法組合,即能在不升級硬體前提下,榨乾 DB2 SQL 引擎的效能潛力。

  1. 上一篇文章:
  2. 下一篇文章:
Copyright © 程式碼之家 All Rights Reserved