WHERE条件中的CASE或AND / OR。什么是最佳做法?

时间:2012-07-30 15:11:46

标签: sql-server tsql

我经常遇到这样的情况:我可以像这样编写t-sql查询的条件......

DECLARE @FirstName NVARCHAR(500)    
SET @FirstName ='Joe'

SELECT * 
FROM dbo.Customers c
WHERE 
    CASE 
        WHEN  @FirstName <> ''  THEN
            CASE WHEN c.FirstName= @FirstName THEN 1 ELSE 0 END
        ELSE 1
     END = 1 

或者像这样...

SELECT * 
FROM dbo.Customers c
WHERE 
    (@FirstName = ''  OR (@FirstName <> '' AND c.FirstName = @FirstName))

它们都产生相同的结果,并且两个查询计划看起来都是相同的。

所以我很好奇哪一个是最佳实践,或者是否有一个与另一个有任何陷阱?

3 个答案:

答案 0 :(得分:3)

我认为这也是关于这种情况下的可读性,但是你在第一个查询示例中做得更多。您强制数据库创建每行0或1的值,并要求数据库检查值是0还是1.在我看来,创建查询时,步骤越少越好。

我会选择第二种方法,尽管你可以摆脱@ FirstName&lt;&gt; ''因为它是不必要的,所以你的查询会更清楚:

SELECT * 
FROM dbo.Customers c
WHERE 
    (@FirstName = ''  OR c.FirstName = @FirstName)
编辑:马丁史密斯提供了一个你可能想要考虑的非常好的见解。

答案 1 :(得分:0)

我更喜欢第二种变体 - 将变量默认为null,因为在最近的SQL Server构建中有一个特定的优化可以优化它。

DECLARE @FirstName NVARCHAR(500) = NULL

SELECT * 
FROM dbo.Customers c
WHERE 
    (@FirstName IS NULL OR c.FirstName = @FirstName)

有关详细信息,请参阅此SO答案:https://stackoverflow.com/a/3415629/1564603

答案 2 :(得分:0)

如何使用LIKE来避免Null Mathing?

DECLARE @FirstName NVARCHAR(500)= NULL

SELECT * 来自dbo.Customers c 哪里     (c.FirstName LIKE @FirstName +'%')

我认为结果可能是相同的,甚至更有趣 无论搜索的时间成本是否更长