2012-07-20 122 views
0

好,我有如下表称为Foo这是一个复杂PIVOT查询SQL动态WHERE子句

Example Result Set

我需要删除该表具有行(DB1,DB2,DB3的输出)全部NULL。要做到这一点,我们通常可以使用类似

DELETE FROM Foo 
WHERE [DB1] IS NULL 
    AND [DB2] IS NULL 
    AND [DB3] IS NULL; 

但问题是,这个代码是从C#和列(DB1,DB2,DB3)呼吁将执行到执行改变。

我该如何动态地做到这一点?

谢谢你的时间。

Edit1。我有另一个表Bar,其中包含可用的DB#列,因此可以使用此表SELECT DISTINCT ...获取我在WHERE子句中需要的列的列表。但是,我从来没有这样做过,不知道从哪里开始...任何帮助表示赞赏。

Edit2。我无法以任何方式使用C#。 C#代码是SQL的解析器,可以与给定的.sql文件一起使用。这必须完全在SQL中完成。

回答

1

sp_executesql允许您执行SQL脚本中构建的SQL字符串。

http://msdn.microsoft.com/en-us/library/ms188001.aspx

从你的表吧

create proc DumpFooJunk 
as 
begin 
    declare @strCols nvarchar(max) 
    select @strCols = N'' 
    select @strCols = @strCols + ' AND ' + name + ' IS NULL ' from [bar] 
    select @strCols = N'DELETE FROM [foo] WHERE ' + substring(@strCols,5,LEN(@strcols)) 
    select @strCols 
    -- exec sp_executesql @strCols 
end 
+0

谢谢你。它给了我一些想法,但这里仍然存在名称问题。如何得到它?你的子串从5开始,为什么?名称的长度(即DB1等)是可变长度的。谢谢你的时间。 – MoonKnight 2012-07-20 15:25:26

+0

该字符串从5开始,因为它在开始时由一个额外的'AND'构建。如果你想要的话,你可以把这段代码放到一个存储过程中,并按照这种方式调用 - 参见编辑。或者你的意思是如何到达sql?只需取消注释sp_execute sql行。 – podiluska 2012-07-20 15:31:52

+0

它将在SP中。但问题仍然存在,即使您提供了什么 - 我如何获取所需的列名。请参阅Edit1。再次感谢您的时间。 – MoonKnight 2012-07-20 15:33:39

1

您可以使用StringBuilder动态构建WHERE子句,假定C#代码知道应该出现在输出中的列。

通常,当您这样做时,您希望在动态WHERE子句中包含参数占位符,并动态地将参数添加到查询中以避免SQL注入。但是,在这种情况下,没有变量值。只需在C#中动态连接WHERE子句的各个部分即可。

+0

由于各种原因,我无法使用C#来帮助我。 C#代码是SQL的解析器,可以即时执行SQL脚本文件。这必须在SQL脚本文件中完成。谢谢你的时间。 – MoonKnight 2012-07-20 15:06:50

0

试图通过他们的指数值以获得列,如果他们总是在相同的位置,并得到了列标题名称,然后使用构造SQL语句他们。

例如

string colHeader1 = (string)dr[3]; 
string colHeader2 = (string)dr[4]; 
string colHeader3 = (string)dr[5]; 
+0

我无法使用C#。请参阅我上面提出的评论。非常感谢...... – MoonKnight 2012-07-20 15:29:16

1

除了动态构建WHERE,你也可以尝试这样的事:

DELETE FROM Foo 
WHERE 
    (0 = @db1 AND [DB1] IS NULL) 
    AND (0 = @db2 AND [DB2] IS NULL) 
    AND (0 = @db3 AND [DB3] IS NULL) 
    -- Etc... 
; 

通过设置绑定参数@db_为0,则可以有效地“关闭”相应IS NULL。因此,只需将那些需要测试的值设置为不同于0的值。

+0

谢谢,但在这个阶段,我不能假定名称(DB1,DB2等)会一致(它们可能是任何东西),并且可能有任何数量的名称。就像我在编辑中所说的,我可以从另一个表'Bar'中获得这些名称,我可以在其中选择'DISTINCT ...',但是我仍然对如何构建需要的WHERE子句感到迷茫。感谢您的时间... – MoonKnight 2012-07-20 15:28:28

+0

@Killercam你是说你实际存储字段_names_在其他表?如果是的话,你有更大的问题;)如果不是,只需列出这个'WHERE'中的所有可能的字段。 – 2012-07-20 16:02:46

+0

我已经接受了上面的答案。事实上,我从另一张桌子上得到它,我不知道如何做到这一点,@podiluska 想出了一个奇妙的解决方案!感谢你的宝贵时间... – MoonKnight 2012-07-20 16:12:20