2025年9月25日: PostgreSQL 18 釋出!
支援的版本: 當前 (18) / 17 / 16 / 15 / 14 / 13
開發版本: devel
不支援的版本: 12 / 11 / 10 / 9.6

15.4. 並行安全 #

規劃器將查詢涉及的操作分為“並行安全”、“並行受限”或“並行不安全”。並行安全的操作是指不與並行查詢的使用衝突的操作。並行受限的操作是指不能在並行工作程序中執行,但可以在領導程序中執行(當並行查詢正在使用時)的操作。因此,並行受限的操作永遠不會出現在 GatherGather Merge 節點下方,但可以出現在包含這些節點的計劃的其他地方。並行不安全的操作是指即使在領導程序中也不能在並行查詢使用時執行的操作。當查詢包含任何並行不安全的操作時,該查詢將完全停用並行查詢。

以下操作始終是並行受限的:

  • 公共表表達式 (CTE) 的掃描。

  • 臨時表的掃描。

  • 外部表的掃描,除非外部資料包裝器具有 IsForeignScanParallelSafe API 表明情況並非如此。

  • 引用相關 SubPlan 的計劃節點。

15.4.1. 函式和聚合的並行標記 #

規劃器無法自動確定使用者定義的函式或聚合是並行安全、並行受限還是並行不安全,因為這需要預測函式可能執行的每一種操作。通常,這等同於停機問題,因此是不可能的。即使是簡單的函式,如果可能的話,我們也嘗試過,但這將是昂貴且容易出錯的。相反,除非另有標記,否則所有使用者定義的函式都假定為並行不安全。在使用 CREATE FUNCTIONALTER FUNCTION 時,可以透過指定適當的 PARALLEL SAFEPARALLEL RESTRICTEDPARALLEL UNSAFE 來設定標記。在使用 CREATE AGGREGATE 時,可以將 PARALLEL 選項指定為 SAFERESTRICTEDUNSAFE 作為相應的值。

如果函式寫入資料庫、更改事務狀態(透過使用子事務進行錯誤恢復以外的方式)、訪問序列或對設定進行永續性更改,則必須將函式和聚合標記為 PARALLEL UNSAFE。類似地,如果函式訪問臨時表、客戶端連線狀態、遊標、預備語句或系統無法在工作程序之間同步的各種後端本地狀態,則必須將函式標記為 PARALLEL RESTRICTED。例如,setseedrandom 就是因為最後這個原因而被標記為並行受限的。

通常,如果一個函式被標記為安全但實際上是受限的或不安全的,或者被標記為受限但實際上是不安全的,那麼在並行查詢中使用時,它可能會引發錯誤或產生錯誤的結果。C 語言函式如果標記不當,理論上可能會表現出完全未定義的行為,因為系統無法保護自己免受任意 C 程式碼的侵害,但在大多數情況下,結果不會比任何其他函式更糟。如有疑問,最好將函式標記為 UNSAFE

如果在並行工作程序中執行的函式獲取了領導程序未持有的鎖(例如,透過查詢查詢中未引用的表),則這些鎖將在工作程序退出時釋放,而不是在事務結束時釋放。如果您編寫了一個執行此操作的函式,並且這種行為差異對您很重要,請將此類函式標記為 PARALLEL RESTRICTED,以確保它們僅在領導程序中執行。

請注意,查詢規劃器不會考慮推遲執行查詢中涉及的並行受限函式或聚合,以獲得更好的計劃。因此,例如,如果應用於特定表的 WHERE 子句是並行受限的,查詢規劃器將不會考慮在計劃的並行部分中執行對該表的掃描。在某些情況下,可以在查詢的並行部分中包含對該表的掃描,並將 WHERE 子句的評估推遲到 Gather 節點之上執行(這可能甚至更有效)。但是,規劃器不會這樣做。

提交更正

如果您在文件中看到任何不正確、與您對特定功能的體驗不符或需要進一步澄清的內容,請使用 此表單 報告文件問題。