在SQL Server中检查输入参数是否为Null并在where语句中使用它

64

如何在WHERE子句中包含输入参数但如果该参数为空则排除它?

我相信有许多方法,但我似乎想不起来了。

我可以使用COALESCE()吗?但我认为这只用于选择值?

编辑

为了澄清,假设有一个名为@code ="1"的变量,然后我的WHERE会是Where type='B' AND code = @code,但如果@code为null,那么我只想要Where type='B' - 注意缺少的code = @code


你可以使用 WHERE COALESCE(code =@code,true)。但我不是数据库专家,不确定这个答案是否好:D。 - Andrii Plotnikov
@Sarief 谢谢,但是TSQL没有布尔数据类型。它只能使用非布尔值的关系运算符,所以您的建议不幸地行不通。 - Suncat2000
7个回答

102
你可以使用 IsNull 函数。
 where some_column = IsNull(@yourvariable, 'valueifnull')

编辑:

你在评论中描述的可以像这样完成:

where (@code is null or code = @code)

3
谢谢,我的意思是假设有一个名为@code的变量,值为"1",那么我的查询条件就是"Where type='B' AND code = @code"。但是如果@code为空,那么我只想要"Where type='B'" —— 注意缺失的代码 = @code。 - Martin
2
你可以在编写查询语句时使用 where some_column = IsNull(@yourvariable, some_column),其中 IsNull 函数的第二个参数为 some_column,以获取所有查询结果而不进行过滤,如果 @yourvariable 为空。 - Rohim Chou

16

这是另一种方法:

SELECT * FROM Thingies WHERE ( @thingId IS NULL OR ThingID = @thingId )

2
遗憾的是,整个表达式将被评估。在TSQL中没有快捷方式。不过您的表达式是正确的。 - Suncat2000

11

怎么样?

WHERE (Column1 = @Var1 OR @Var1 IS NULL)
AND (Column2 = @Var2 OR @Var2 IS NULL)

5

我想提供一个解决方案,该方案源自于另一个网站

SELECT * FROM Thingies 
WHERE ThingID = isnull(@ThingId,ThingID)

使用此解决方案,如果用户选择将您的参数设为null,那么您的查询将返回所有行作为结果。


5
这个问题对我来说非常有帮助,因为我们团队中有一些人曾经为类似的问题挠头。我将其记录下来以备他人参考,在使用同样的方法时遇到问题时能够找到解决方法。
我试图只在@Parameter不为空时评估多部分WHERE子句的一部分。我尝试了以下方法,但如果@Parameter为空,则始终没有行被返回。
DECLARE @Parameter int = null;

SELECT  *  FROM  TABLE
WHERE   [AlternateID] is not null 
        AND (@Parameter is not null AND [AlternateID] = @Parameter)

我曾经错误地认为(@Parameter 不是 null 并且 [AlternateID] = @Parameter)如果 @Parameter 是 null,它将不会成为完整的 WHERE 子句的一部分。但实际上它会导致整个 WHERE 子句返回 false。解决方法如下,需要添加 OR 1=1:

WHERE   [AlternateID] is not null 
        AND (@Parameter is not null AND [AlternateID] = @Parameter OR 1=1)

当然,阿里(声望不足无法点赞)所概述的方法可以更高效地解决这个问题。
WHERE   [AlternateID] is not null 
        AND [Partner_Customer_ID] = ISNULL(@Parameter, [Partner_Customer_ID])    

1
另一种方法是: WHERE IsNull([AlternateID], 0) = Coalesce((@Parameter, [AlternateID], 0)然而,为了获得最佳性能,动态SQL将是更好的选择,因为索引查找的机会将会增加。 - SteveD

2
您可以使用ISNULL()函数或像其他人一样明确检查null。只要您没有超过1或2个可选输入参数,这是可以的。但是,如果有更多参数,则此方法将非常低效,因为您创建的索引将不会像您期望的那样被使用。在这种情况下,我建议使用动态SQL。这是一篇很好的文章,解释了为什么需要使用catch-all queries

0

我觉得这会有帮助

@id 
@name

SELECT [Id],[Name] FROM [Person] 
WHERE Id = @id and ISNULL(@name, Name)

这将允许您忽略名称条件,如果它为空。

网页内容由stack overflow 提供, 点击上面的
可以查看英文原文,
原文链接