表達式中的類型轉換可能會影響“CardinalityEstimate” - 在計算列上?
我看了一下這個問題:
表達式中的類型轉換可能會影響查詢計劃選擇中的“CardinalityEstimate”?
但這與排序規則有關,與計算列無關。
我在下面的查詢中使用了以下表定義,這給了我一個查詢提示
表達式中的類型轉換 (CONVERT(varchar(10),
$$ t $$.$$ FLTCD_FLT_DATE $$,112)) 可能會影響查詢計劃選擇中的“CardinalityEstimate”
請注意計算列
flightReference
CREATE TABLE [dbo].[repl_Transportation] ( [FLIGHT#] INT NOT NULL, [FLTCD_FLT_DATE] DATETIME NULL, [FLTCD_DEP_GATE] CHAR(3) NULL, [FLTCD_ARR_GATE] CHAR(3) NULL, [FLTCD_SEQUENCE] CHAR(1) NULL, [DIRECTION] CHAR(1) NULL, [PNR_NUMBERS] VARCHAR(70) NULL, [HK] NUMERIC(3,0) NULL, [Create_Date] DATETIME NOT NULL, [Modify_Date] DATETIME NULL, [flightReference] AS (substring(((CONVERT([varchar](10),[FLTCD_FLT_DATE], (112))+[FLTCD_DEP_GATE])+[FLTCD_ARR_GATE])+[FLTCD_SEQUENCE],(3),(13))) PERSISTED, CONSTRAINT [PK_FLIGHT#] PRIMARY KEY CLUSTERED ([FLIGHT#] asc)) IF OBJECT_ID('[dbo].[repl_Transportation_Details]') IS NOT NULL DROP TABLE [dbo].[repl_Transportation_Details] GO CREATE TABLE [dbo].[repl_Transportation_Details] ( [FLT_LEG_ID] INT NOT NULL, [FLIGHT#] INT NOT NULL, [LEG_NO] TINYINT NULL, [AIRLINE_CODE] CHAR(2) NULL, [AIRLINE_FLTNO] VARCHAR(6) NULL, [DEP_DATE_TIME] DATETIME NULL, [ARR_DATE_TIME] DATETIME NULL, [DEP_AIRPORT] CHAR(3) NULL, [ARR_AIRPORT] CHAR(3) NULL, [Create_Date] DATETIME NULL, [Modify_Date] DATETIME NULL, CONSTRAINT [PK_FLT_LEG_ID] PRIMARY KEY CLUSTERED ([FLT_LEG_ID] asc))
當我執行以下查詢時,我在選擇時收到警告: 查詢計劃在這裡
表達式中的類型轉換 (CONVERT(varchar(10),
$$ t $$.$$ FLTCD_FLT_DATE $$,112)) 可能會影響查詢計劃選擇中的“CardinalityEstimate”
SELECT t.FLIGHT#, t.flightReference, PNR_NUMBERS, MIN(td.DEP_DATE_TIME) AS departDate, MAX(td.ARR_DATE_TIME) AS arrivalDate, CASE WHEN PNR_NUMBERS IS NULL OR PNR_NUMBERS = '' THEN 'Paper Ticket' ELSE 'E-Ticket' END AS ticketType, 'US' AS source, 0 as sourceId, DIRECTION, FLTCD_DEP_GATE, FLTCD_ARR_GATE FROM repl_Transportation AS t LEFT JOIN repl_Transportation_Details AS td ON td.FLIGHT# = t.FLIGHT# GROUP BY t.FLIGHT#, t.flightReference, PNR_NUMBERS, DIRECTION, FLTCD_DEP_GATE, FLTCD_ARR_GATE
當我從選擇中刪除 MIN 和 MAX 列時,不再有任何警告,查詢計劃在這裡
SELECT t.FLIGHT#, t.flightReference, PNR_NUMBERS, --MIN(td.DEP_DATE_TIME) AS departDate, --MAX(td.ARR_DATE_TIME) AS arrivalDate, CASE WHEN PNR_NUMBERS IS NULL OR PNR_NUMBERS = '' THEN 'Paper Ticket' ELSE 'E-Ticket' END AS ticketType, 'US' AS source, 0 as sourceId, DIRECTION, FLTCD_DEP_GATE, FLTCD_ARR_GATE FROM repl_Transportation AS t LEFT JOIN repl_Transportation_Details AS td ON td.FLIGHT# = t.FLIGHT# GROUP BY t.FLIGHT#, t.flightReference, PNR_NUMBERS, DIRECTION, FLTCD_DEP_GATE, FLTCD_ARR_GATE
有什麼辦法可以擺脫這個警告嗎?
它是一個持久列,轉換已經完成,為什麼查詢優化器還在繼續呢?
我看了一下這個問題:
表達式中的類型轉換可能會影響查詢計劃選擇中的“CardinalityEstimate”?
但這與排序規則有關,與計算列無關。
這是同一個問題。該警告是資訊性的,可幫助您了解在基數估計中可能注意到的任何問題。
有什麼辦法可以擺脫這個警告嗎?
它是一個持久列,轉換已經完成,為什麼查詢優化器還在繼續呢?
僅僅因為計算列是持久化的,並不意味著優化器會選擇使用持久化的值。SQL Server 例行地在編譯過程開始時將計算列(持久或不持久)擴展為基礎定義。稍後,它可能會將表達式匹配回可用的持久計算列,也可能不匹配。當優化器遇到表達式時,它可能會在計劃中添加警告。
防止這種擴展和匹配的唯一方法是在合適的版本上啟用跟踪標誌 176 。
當我從選擇中刪除
MIN
和MAX
列時,不再有任何警告通過此更改,優化器能夠簡化查詢以刪除不必要的連接。結果是一個
TRIVIAL
計劃,沒有基於成本的選擇,因此沒有關於計劃選擇的警告。