从XML父节点获取SQL值(单独)

时间:2012-11-20 14:18:14

标签: sql sql-server

在我的下面的Query中,它将所有重新设置的XML作为XML返回到单个变量中。但是我需要将所有父节点值分成while循环。只需运行以下查询:

---------只是声明临时表--------------------------------- ----------------

IF OBJECT_ID('tempdb.dbo.##TestTable','U')IS NOT NULL DROP TABLE ##TestTable
CREATE TABLE ##TestTable(id int,Uname nvarchar(max),Uaddress nvarchar(max))
INSERT INTO ##TestTable values (1,'abc','NY')
INSERT INTO ##TestTable values (2,'def','WD')
INSERT INTO ##TestTable values (3,'','KL')

DECLARE @XML XML
DECLARE @WhereClause nvarchar(max)
DECLARE @CountVal int
SELECT @CountVal=count(*) from ##TestTable
SET  @XML= (SELECT * FROM ##TestTable FOR XML PATH('ParentNode'), ELEMENTS XSINIL)
SELECT @XML
;with cte as
( select xr.value('fn:local-name(.)','nvarchar(max)') name, xr.value('.','nvarchar(max)') val  from @xml.nodes('//.') xq(xr)
    where xr.value('fn:local-name(.)','nvarchar(max)')<>''
)
SELECT @WhereClause= STUFF((select ' and ' + name + '='''+val+'''' from cte for xml path('')),1,4,'')
SELECT @WhereClause

WHILE (@CountVal>0)
BEGIN
    SELECT @WhereClause
    SET @CountVal=@CountVal-1
END
IF OBJECT_ID('tempdb.dbo.##TestTable','U')IS NOT NULL DROP TABLE ##TestTable

当前样本XML(在@XML中):

<ParentNode xmlns:xsi="http://www.w3.org/2001/XMLSchema-instance"><id>1</id><Uname>abc</Uname><Uaddress>NY</Uaddress></ParentNode><ParentNode xmlns:xsi="http://www.w3.org/2001/XMLSchema-instance"><id>2</id><Uname>def</Uname><Uaddress>WD</Uaddress></ParentNode><ParentNode xmlns:xsi="http://www.w3.org/2001/XMLSchema-instance"><id>3</id><Uname /><Uaddress>KL</Uaddress></ParentNode>

当前@WhereClause的输出是(全部放在一个@WhereClause变量中):

ParentNode='1abcNY' and id='1' and Uname='abc' and Uaddress='NY' and ParentNode='2defWD' and id='2' and Uname='def' and Uaddress='WD' and ParentNode='3KL' and id='3' and Uname='' and Uaddress='KL'

但我的预期输出是:

Firstly(in @WhereClause): id='1' and Uname='abc' and Uaddress='NY'
Secondly(in @WhereClause):id='2' and Uname='def' and Uaddress='WD'
Thirdly(in @WhereClause):id='3' and Uname='' and Uaddress='KL'

我是怎么做到的。提前谢谢。

2 个答案:

答案 0 :(得分:3)

试试这个:

declare @WhereClause nvarchar(max)
declare @CountVal int

select @CountVal=count(*)
from ##TestTable

while @CountVal>0
begin
    select @WhereClause =
           (
             select ' and '+T.N.value('local-name(.)', 'nvarchar(max)')+'='+T.N.value('.', 'nvarchar(max)')
             from (
                    select *
                    from ##TestTable
                    where id = @CountVal
                    for xml path(''), type
                  ) as C(X)
               cross apply C.X.nodes('/*') as T(N)
             for xml path(''), type
           ).value('substring((./text())[1], 6)', 'nvarchar(max)')

    select @WhereClause
    set @CountVal=@CountVal-1
end

答案 1 :(得分:2)

似乎迟到了,误解了,这本来就是我的方法

DECLARE @XML XML
DECLARE @WhereClause nvarchar(max)
DECLARE @CountVal int
SELECT @CountVal=count(*) from ##TestTable
SET  @XML= (SELECT * FROM ##TestTable FOR XML PATH('ParentNode'), ELEMENTS XSINIL)
SELECT @XML
;with cte as
( select xr.value('fn:local-name(.)','nvarchar(max)') name, xr.value('.','nvarchar(max)') val  from @xml.nodes('//.') xq(xr)
    where xr.value('fn:local-name(.)','nvarchar(max)')<>'' and xr.value('fn:local-name(.)','nvarchar(max)')<>'ParentNode'
)



SELECT @WhereClause= SubString((select Case when Name ='id'  then   CHAR(10) +''+ name + '='''+val+'''' else  ' and ' + name + '='''+val+'''' end from cte for xml path('')),2,100000000)
Print  @WhereClause