条款有或没有数据的变量

时间:2016-04-15 14:20:19

标签: sql-server

如何在结果中包含或排除数据。

我有一个表中包含许多值的表。我想显示所有值“结束”或所有值没有“结束”。我的开关“@end”也有一个变量。

如果它的值为“310”,程序应该以“结束”显示所有内容。如果它有另一个值,程序应该显示我没有“结束”。

我试过这样的事情:

where CASE @END WHEN 310 THEN m.LONR = @ENDE ELSE m.LONR <> 310 END

似乎在带有case的where子句中无法使用运算符。

我在这里找不到任何相同的答案,或者我不明白。

谢谢jens

1 个答案:

答案 0 :(得分:1)

您可以简单地使用OR

,而不是案例表达式
WHERE   (@End = 310 AND m.LONR = 310)
OR      (@End <> 310 AND m.LONR <> 310)

值得注意的是,在NULL值的情况下,谓词都不会评估为true,因此如果变量或列可以为空,您可能希望使用:

WHERE   (@End = 310 AND m.LONR = 310)
OR      (ISNULL(@End, 0) <> 310 AND ISNULL(m.LONR, 0) <> 310);

如果m.LONR被编入索引,那么使用IF分割案例几乎肯定是有益的:

IF (@End = 310)
BEGIN
    SELECT  <columns>
    FROM    <tables>
    WHERE   m.LONR = 310;
END
ELSE
BEGIN
    SELECT  <columns>
    FROM    <tables>
    WHERE   m.LONR <> 310;
END

或使用UNION ALL

SELECT  <columns>
FROM    <tables>
WHERE   m.LONR = 310
AND     @End = 310;
UNION ALL
SELECT  <columns>
FROM    <tables>
WHERE   m.LONR <> 310
AND     @End <> 310;  --OR ISNULL(@End, 0) <> 310 to deal with NULLs

原因是SQL Server将基于@End创建一个未知的计划,因此在编译时不知道它是否会被过滤:

m.LONR = 310

m.LONR <> 310

因此无法有效地规划索引是否寻找,或者表扫描是否更有效。分离逻辑将允许最有效的计划用于每个场景。