我繼承了一個我希望優化的舊SQL腳本,但經過多次測試後,我必須承認,我所有的測試都只是用重複塊創建大型SQL。我想知道是否有人可以針對以下模式提出更好的代碼(請參閱下面的代碼)。我不想使用臨時表(WITH)。爲了簡單起見,我只放了3個級別(表TMP_C,TMP_D和TMP_E),但原始SQL有8個級別。用於NOT IN的TSQL優化代碼
WITH
TMP_A AS (
SELECT
ID,
Field_X
FROM A
TMP_B AS(
SELECT DISTINCT
ID,
Field_Y,
CASE
WHEN Field_Z IN ('TEST_1','TEST_2') THEN 'CATEG_1'
WHEN Field_Z IN ('TEST_3','TEST_4') THEN 'CATEG_2'
WHEN Field_Z IN ('TEST_5','TEST_6') THEN 'CATEG_3'
ELSE 'CATEG_4'
END AS CATEG
FROM B
INNER JOIN TMP_A
ON TMP_A.ID=TMP_B.ID),
TMP_C AS (
SELECT DISTINCT
ID,
CATEG
FROM TMP_B
WHERE CATEG='CATEG_1'),
TMP_D AS (
SELECT DISTINCT
ID,
CATEG
FROM TMP_B
WHERE CATEG='CATEG_2' AND ID NOT IN (SELECT ID FROM TMP_C)),
TMP_E AS (
SELECT DISTINCT
ID,
CATEG
FROM TMP_B
WHERE CATEG='CATEG_3'
AND ID NOT IN (SELECT ID FROM TMP_C)
AND ID NOT IN (SELECT ID FROM TMP_D))
SELECT * FROM TMP_C
UNION
SELECT * FROM TMP_D
UNION
SELECT * FROM TMP_E
非常感謝您的幫助。
不是'NOT IN'上'TMP_D'的'WHERE'條款的其他部分和'TMP_E'多餘的?由於類別不重疊,如'TMP_B'中定義的,在隨後的查詢中不需要檢查除類別以外的任何內容。這使得它們看起來像只在'UNION'返回時纔會過濾'CATEG_4'。 (是的,'distinct'在那裏。) – HABO 2013-05-09 15:39:27
@HABO:如果ID是唯一的,它們將是多餘的,但事實並非如此。不幸的是,ID不是唯一的,我們可以使用ID = 10和Field_Z = TEST_1的記錄,也可以使用ID = 10但Field_Z = TEST_3的記錄。 – Bouzouki 2013-05-09 17:16:51