SQL Server 2005:在ISNULL条件下选择语句

时间:2010-07-18 17:14:53

标签: sql sql-server sql-server-2005 tsql

环境:SQL Server 2005

我有一个存储过程,它在一个参数中接收逗号分隔值。我在SQL中编写了一个Table Valued UDF函数来打破它并将其作为表返回给我。我正在使用该值来过滤存储过程的where子句中的数据。一切正常,直到传递给存储过程的逗号分隔变量中有NULL。我想以这样的方式编写我的where子句,如果传递的变量是NULL,那么它不应该使用Split函数。这是我在存储过程中所做的事情。

Declare @list varchar(100), @Col2 varchar(100)

SELECT  *
  FROM  Table1 t1
INNER JOIN dbo.Table2 t2 ON t1.Col1 = t2.Col1
WHERE t1.Col2 = ISNULL(@Col2,t1.Col2)
--I want to write below condition the same way i have written the above condition
    AND t1.Col3 IN (select * from dbo.SplitMe(@list))

有没有办法按照Col2的选择方式编写选择Col3的条件?

3 个答案:

答案 0 :(得分:2)

如果想法是Col3如果@list为空,则无法过滤,那么可以以相同的方式执行

Declare @list varchar(100), @Col2 varchar(100)

SELECT  *
  FROM  Table1 t1
INNER JOIN dbo.Table2 t2
on t1.Col1 = t2.Col1

where t1.Col2 = ISNULL(@Col2,t1.Col2)
AND (@list IS NULL OR  t1.Col3 IN (select * from dbo.SplitMe(@list)))

但除非表格非常小​​,否则不是一个好主意。对于计划缓存的原因,通常最好将所有这些排列分解为它们自己的SQL语句,而不是尝试编写一个适合所有类型的查询或(如果排列的数量太大)考虑使用动态SQL(请参阅{{3} })

请注意,此保证不会调用Split函数。没有保证的条款评估顺序。但它确实意味着如果它被调用它将对查询的结果没有影响。 (编辑当然假设当NULL实际上不会导致某种错误时被调用c.f. Remus的评论)

答案 1 :(得分:1)

您现在有一个查询,现在有两个彼此独立的变量。在单个查询中包含它们会产生一个不可搜索的查询 - 查询根据变量值而有很大差异,并且您使用昂贵的条件表达式将它们保持在一起。这既是痛苦的维持,也是表现不佳。

您可以使用IF语句:

IF
BEGIN

    SELECT *
       FROM TABLE1 t1
       JOIN TABLE2 t2 ON t2.col1 = t1.col1
     WHERE t1.col1 = COALESCE(@col2, t1.col2)

END
ELSE
BEGIN

    SELECT *
       FROM TABLE1 t1
       JOIN TABLE2 t2 ON t2.col1 = t1.col1
      WHERE t1.col2 = COALESCE(@col2, t1.col2)
          AND t1.col3 IN (SELECT * FROM dbo.splitme(@list))

END

...但仍有空处理。对于两个变量,这是四个可能的价值结果。像这样的情况是动态SQL的意图 - 构建必要的查询,因为拖拽行李不能很好地执行。

答案 2 :(得分:1)

WHERE (t1.Col2 = @Col2 OR @Col2 IS NULL)
AND (t1.Col3 IN (select * from dbo.SplitMe(@list)) OR @list IS NULL)