建立和解譯查詢計劃 - Amazon Redshift

本文為英文版的機器翻譯版本,如內容有任何歧義或不一致之處,概以英文版為準。

建立和解譯查詢計劃

您可以使用查詢計畫來取得執行查詢所需的個別操作的相關資訊。使用查詢計畫之前,建議您先了解 Amazon Redshift 如何處理處理中的查詢和建立查詢計畫。如需詳細資訊,請參閱查詢計劃和執行工作流程

若要建立查詢計畫,請執行 EXPLAIN 命令,後面接著實際的查詢文字。查詢計畫可提供下列資訊:

  • 執行引擎將執行的操作,請由下至上閱讀結果。

  • 每個操作會執行的步驟類型。

  • 每個操作中使用的資料表和資料欄。

  • 每個操作中處理的資料量,就資料列的數量和資料寬度 (位元組) 而言。

  • 操作的相對成本。成本是一種測量方式,會比較計畫內步驟的相對執行時間。成本不會提供實際執行時間或記憶體消耗的任何精確資訊,也不會提供執行計畫之間有意義的比較。但它可提供您查詢中耗費最多資源的操作的指示。

EXPLAIN 命令實際上不會執行查詢。它只會顯示如果查詢是在目前操作條件下執行時,Amazon Redshift 會執行的計畫。如果您變更資料表的結構描述或資料,並再次執行 ANALYZE 以更新統計資訊中繼資料,查詢計畫可能不同。

的查詢計畫輸出EXPLAIN是查詢執行的簡化、高階檢視。它不會說明平行查詢處理的詳細資訊。若要查看詳細資訊,請執行查詢本身,然後從 SVL_QUERY_SUMMARY 或 SVL_QUERY_REPORT 檢視取得查詢摘要資訊。如需使用這些檢視的相關資訊,請參閱分析查詢摘要

下列範例顯示EVENT資料表上簡單 GROUP BY 查詢的EXPLAIN輸出:

explain select eventname, count(*) from event group by eventname; QUERY PLAN ------------------------------------------------------------------- XN HashAggregate (cost=131.97..133.41 rows=576 width=17) -> XN Seq Scan on event (cost=0.00..87.98 rows=8798 width=17)

EXPLAIN 會針對每個操作傳回下列指標:

成本

用在計畫內比較操作的相對值。成本由兩個小數值組成,以兩個句點分隔,例如 cost=131.97..133.41。第一個值,在此情況下的 131.97,提供傳回此操作第一個資料列的相對成本。第二個值,在此情況下的 133.41,提供完成操作的相對成本。查詢計畫中的成本會在您讀取計畫時累積,因此此範例 (131.97..133.41) 中的 HashAggregate 成本包含其下方的 Seq 掃描成本 (0.00..87.98)。

資料列

要傳回的估計資料列數量。在此範例中,掃描預期傳回 8798 個資料列。 HashAggregate 運算子會自行傳回 576 列 (從結果集中捨棄重複的事件名稱之後)。

注意

資料列估算是根據 ANALYZE命令產生的可用統計資料。如果 最近ANALYZE尚未執行,則預估值較不可靠。

寬度

估計的平均資料列寬度 (位元組)。在此範例中,平均資料列的寬度預期為 17 個位元組。

EXPLAIN 運算子

本節簡短說明您在EXPLAIN輸出中最常看到的運算子。如需運算子的完整清單,請參閱 SQL命令一節EXPLAIN中的 。

循序掃描運算子

循序掃描運算子 (Seq Scan) 指出資料表掃描。序列掃描會從頭到尾依序掃描資料表中的每個資料欄,並評估每一列的查詢限制 (子WHERE句中)。

聯結運算子

Amazon Redshift 會根據要聯結資料表的實體設計、聯結所需的位置資料,以及查詢本身的特定需求來選取聯結運算子。

  • 巢狀迴路

    最差的最佳聯結,巢狀迴路主要用於交叉聯結 (笛卡兒乘積) 和一些對等聯結中。

  • 雜湊聯結和雜湊

    雜湊聯結和雜湊通常會較巢狀迴路聯結更快速,用於內部聯結和左右外部聯結。當聯結資料表中的聯結資料欄不是散發索引鍵也不是排序索引鍵時,會使用這些運算子。雜湊運算子會為聯結中的內部資料表建立雜湊表;雜湊聯結運算子會讀取外部資料表、雜湊聯結資料欄,並在內部雜湊表中尋找相符項目。

  • 合併聯結

    合併聯結通常是最快速的聯結,用於內部聯結和外部聯結。合併聯結不會用於完整聯結。當聯結資料表中的聯結資料欄為散發索引鍵也是排序索引鍵,並且少於 20% 的聯結資料表未排序時,會使用此運算子。它會依序讀取兩個排序的資料表,並尋找相符的資料列。若要檢視未排序資料列的百分比,請查詢 SVV_TABLE_INFO 系統資料表。

  • 空間聯結

    通常基於空間資料的鄰近程度快速聯結,用於 GEOMETRYGEOGRAPHY 資料類型。

彙整運算子

查詢計劃在涉及彙總函數和 GROUP BY 操作的查詢中使用下列運算子。

  • Aggregate

    純量彙總函數的運算子,例如 AVG和 SUM。

  • HashAggregate

    未排序的分組彙整函數的運算子。

  • GroupAggregate

    排序的分組彙整函數的運算子。

排序運算子

查詢計畫會在查詢必須排序或合併結果集時使用下列運算子。

  • 排序

    評估 ORDER BY 子句和其他排序操作,例如UNION查詢和聯結、SELECTDISTINCT查詢和視窗函數所需的排序。

  • 合併

    根據衍生自平行操作中繼排序的結果,產生最終排序的結果。

UNION、 INTERSECT和 EXCEPT運算子

查詢計劃針對涉及使用 UNION、 INTERSECT和 設定操作的查詢使用下列運算子EXCEPT。

  • Subquery

    用於執行UNION查詢。

  • Hash Intersect Distinct

    用於執行INTERSECT查詢。

  • SetOp 除了

    用於執行 EXCEPT(或 MINUS) 查詢。

其他運算子

下列運算子也會經常出現在例行查詢的EXPLAIN輸出中。

  • 唯一

    移除SELECTDISTINCT查詢和UNION查詢的重複項目。

  • 限制

    處理LIMIT子句。

  • 視窗

    執行視窗函數。

  • 結果

    執行未牽涉任何資料表存取的純量函數。

  • Subplan

    用於特定子查詢。

  • 網路

    將中繼結果傳送至領導者節點供進一步處理。

  • Materialize

    儲存資料列以輸入至巢狀迴路聯結和一些合併聯結。

在 中加入 EXPLAIN

取決於查詢和基礎資料表的結構,查詢最佳化器會使用不同的聯結類型來擷取資料表資料。EXPLAIN 輸出會參考聯結類型、使用的資料表,以及資料表資料在叢集間的分佈方式,以描述查詢的處理方式。

聯結類型範例

下列範例顯示查詢最佳化器可以使用的不同聯結類型。查詢計畫中使用的聯結類型取決於所牽涉資料表的實體設計。

範例:雜湊聯結兩個資料表

下列查詢會在 CATID 欄CATEGORY上聯結 EVENT和 。CATID 是 的分佈和排序金鑰,CATEGORY但不是 的分佈和排序金鑰EVENT。雜湊聯結會使用 EVENT作為外部資料表和CATEGORY內部資料表來執行。因為 CATEGORY是較小的資料表,規劃器會在查詢處理期間使用 DS_BCAST_ 將其複本廣播至運算節點INNER。此範例中的聯結成本可說明計畫的多數累積成本。

explain select * from category, event where category.catid=event.catid; QUERY PLAN ------------------------------------------------------------------------- XN Hash Join DS_BCAST_INNER (cost=0.14..6600286.07 rows=8798 width=84) Hash Cond: ("outer".catid = "inner".catid) -> XN Seq Scan on event (cost=0.00..87.98 rows=8798 width=35) -> XN Hash (cost=0.11..0.11 rows=11 width=49) -> XN Seq Scan on category (cost=0.00..0.11 rows=11 width=49)
注意

EXPLAIN 輸出中運算子的對齊縮排有時表示這些操作彼此不依賴,並且可以平行啟動。在上述範例中,雖然EVENT資料表上的掃描和雜湊操作已對齊,但EVENT掃描必須等到雜湊操作完全完成。

範例:合併聯結兩個資料表

下列查詢也會使用 SELECT *,但會聯結 SALES 和 LISTING LISTID欄,其中 LISTID 已設定為兩個資料表的分佈和排序金鑰。已選擇合併聯結,且聯結不需要重新分發資料 (DS_DIST_NONE)。

explain select * from sales, listing where sales.listid = listing.listid; QUERY PLAN ----------------------------------------------------------------------------- XN Merge Join DS_DIST_NONE (cost=0.00..6285.93 rows=172456 width=97) Merge Cond: ("outer".listid = "inner".listid) -> XN Seq Scan on listing (cost=0.00..1924.97 rows=192497 width=44) -> XN Seq Scan on sales (cost=0.00..1724.56 rows=172456 width=53)

下列範例示範相同查詢內不同類型的聯結。如上一個範例所示, SALES 和 LISTING合併已聯結,但第三個資料表 EVENT必須與合併聯結的結果結合雜湊。重申,雜湊聯結會衍生播送成本。

explain select * from sales, listing, event where sales.listid = listing.listid and sales.eventid = event.eventid; QUERY PLAN ---------------------------------------------------------------------------- XN Hash Join DS_BCAST_INNER (cost=109.98..3871130276.17 rows=172456 width=132) Hash Cond: ("outer".eventid = "inner".eventid) -> XN Merge Join DS_DIST_NONE (cost=0.00..6285.93 rows=172456 width=97) Merge Cond: ("outer".listid = "inner".listid) -> XN Seq Scan on listing (cost=0.00..1924.97 rows=192497 width=44) -> XN Seq Scan on sales (cost=0.00..1724.56 rows=172456 width=53) -> XN Hash (cost=87.98..87.98 rows=8798 width=35) -> XN Seq Scan on event (cost=0.00..87.98 rows=8798 width=35)

範例:聯結、彙整和排序

下列查詢會執行 SALES和 EVENT 資料表的雜湊聯結,接著會彙總和排序操作,以說明分組SUM函數和 ORDER BY 子句。初始的排序運算子會在運算節點上平行執行。然後 Network 運算子會傳送結果至領導者節點,在其中,Merge 運算子會產生最終排序的結果。

explain select eventname, sum(pricepaid) from sales, event where sales.eventid=event.eventid group by eventname order by 2 desc; QUERY PLAN --------------------------------------------------------------------------------- XN Merge (cost=1002815366604.92..1002815366606.36 rows=576 width=27) Merge Key: sum(sales.pricepaid) -> XN Network (cost=1002815366604.92..1002815366606.36 rows=576 width=27) Send to leader -> XN Sort (cost=1002815366604.92..1002815366606.36 rows=576 width=27) Sort Key: sum(sales.pricepaid) -> XN HashAggregate (cost=2815366577.07..2815366578.51 rows=576 width=27) -> XN Hash Join DS_BCAST_INNER (cost=109.98..2815365714.80 rows=172456 width=27) Hash Cond: ("outer".eventid = "inner".eventid) -> XN Seq Scan on sales (cost=0.00..1724.56 rows=172456 width=14) -> XN Hash (cost=87.98..87.98 rows=8798 width=21) -> XN Seq Scan on event (cost=0.00..87.98 rows=8798 width=21)

資料重新分佈

聯結的EXPLAIN輸出也會指定資料在叢集周圍移動的方式,以促進聯結。資料可以透過播送或重新配送來移動。在播送中,來自聯結一端的資料值會從每個運算節點複製到每個其他運算節點,使得每個運算節點最終有完整的資料副本。在重新配送中,參與的資料值是從其目前的配量傳送至新配量 (可能在不同的節點上)。資料一般會重新配送以符合參與聯結的其他資料表的散發索引鍵 (如果該散發索引鍵是其中一個聯結資料欄)。如果任何資料表都不具備其中一個聯結資料欄上的散發索引鍵,則會配送兩個資料表,或是將內部資料表播送至每個節點。

EXPLAIN 輸出也會參考內部和外部資料表。會先掃描內部資料表,並出現在較接近查詢計畫底端的位置。內部資料表為對其探測相符項目的資料表。它通常位於記憶體中,且通常是雜湊的來源資料表,如有可能,會是要聯結的兩個資料表中較小的那個。外部資料表為要對內部資料表比對的資料列的來源。通常是從磁碟讀取。查詢最佳化工具會根據ANALYZE命令最新執行的資料庫統計資料,選擇內部和外部資料表。查詢子FROM句中的資料表順序不會決定哪個資料表是內部資料表,哪個是外部資料表。

請在查詢計畫中使用下列屬性來識別資料將移動的方式,以輔助查詢:

  • DS_BCAST_INNER

    將整個內部資料表的副本播送至所有運算節點。

  • DS_DIST_ALL_NONE

    不需要重新分發,因為內部資料表已使用 DISTSTYLE 分發給每個節點ALL。

  • DS_DIST_NONE

    不重新配送任何資料表。共置聯結可行,因為會聯結對應的配量,而不需在節點間移動資料。

  • DS_DIST_INNER

    重新配送內部資料表。

  • DS_DIST_OUTER

    重新配送外部資料表。

  • DS_DIST_ALL_INNER

    整個內部資料表會重新分發至單一切片,因為外部資料表使用 DISTSTYLE ALL。

  • DS_DIST_BOTH

    重新配送這兩個資料表。