有沒有辦法讓你的比較運算子動態化?
例如:
SELECT
*
FROM TABLE
WHERE
IIF(@FLAG_A = 'True', COLUMN_A = @COLUMN_A, COLUMN_A <> @COLUMN_A)
AND IIF(@FLAG_B = 'True', COLUMN_B = @COLUMN_B, COLUMN_B <> @COLUMN_B)
AND IIF(@FLAG_C = 'True', COLUMN_C = @COLUMN_C, COLUMN_C <> @COLUMN_C)
我嘗試了上面的例子,我的引數設定為 @FLAG_A = 'True', @FLAG_B = 'False' @FLAG_C = 'False'
我期待這個查詢運行:
SELECT
*
FROM TABLE
WHERE
COLUMN_A = @COLUMN_A
AND COLUMN_B <> @COLUMN_B
AND COLUMN_C <> @COLUMN_C
但我得到:'='附近的語法不正確。
uj5u.com熱心網友回復:
您需要使用顯式AND和OR邏輯。添加RECOMPILE到該OPTION條款也將是一個可能的好處,因為每組變數的計劃可能會非常不同。
不幸的是,由于您的邏輯,這看起來確實有些混亂:
SELECT {Column List} --Don't use SELECT *
FROM dbo.YourTable
WHERE ((@FLAG_A = 'true' AND COLUMN_A = @COLUMN_A) OR (@FLAG_A <> 'true' AND COLUMN_A <> @COLUMN_A))
AND ((@FLAG_B = 'true' AND COLUMN_B = @COLUMN_B) OR (@FLAG_B <> 'true' AND COLUMN_B <> @COLUMN_B))
AND ((@FLAG_C = 'true' AND COLUMN_C = @COLUMN_C) OR (@FLAG_C <> 'true' AND COLUMN_C <> @COLUMN_C))
OPTION (RECOMPILE);
另一種方法是創建一個引數化的動態陳述句。這可能會執行得更好(并允許快取計劃),但是,確實需要更好的理解:
DECLARE @SQL nvarchar(MAX),
@CRLF nchar(2) = NCHAR(13) NCHAR(10);
SET @SQL = N'SELECT {Column List}' @CRLF
N'FROM dbo.YourTable' @CRLF
N'WHERE ' IIF(@FLAG_A = 'True',N' COLUMN_A = @COLUMN_A', N'COLUMN_A <> @COLUMN_A') @CRLF
N' AND ' IIF(@FLAG_B = 'True',N' COLUMN_B = @COLUMN_B', N'COLUMN_B <> @COLUMN_B') @CRLF
N' AND ' IIF(@FLAG_C = 'True',N' COLUMN_C = @COLUMN_C', N'COLUMN_C <> @COLUMN_C') N';';
--Note the data type are guessed, and you will need to correct these.
EXEC sys.sp_executesql @SQL, N'@COLUMN_A varchar(20), @COLUMN_B varchar(20), @COLUMN_C varchar(20)', @COLUMN_A, @COLUMN_B, @COLUMN_C;
轉載請註明出處,本文鏈接:https://www.uj5u.com/houduan/524789.html
標籤:tsql
上一篇:按日期選擇隨機時段
