我已经研究过广泛粉碎这个xml文件的最佳方法,并且已经接近但不是一直到我想要的。
虽然我更喜欢使用SQL Server,但我正在使用SQL Server 2012并拥有Visual Studio 2012。
以下是我正在使用的XML数据类型的片段。我无法控制XML的构建方式,因为它来自第三方。在节点下面的Reality中,有大约450种响应类型,例如ResponseID,Name,Status等......我只显示大约十种。
<xml>
<Response>
<ResponseID>R_a4yThVvKXzVyftz</ResponseID>
<ResponseSet>Default Response Set</ResponseSet>
<Name>Doe, John</Name>
<ExternalDataReference>0</ExternalDataReference>
<EmailAddress>jdoe@gmail.com</EmailAddress>
<IPAddress>140.123.12.123</IPAddress>
<Status>0</Status>
<StartDate>2014-09-18 09:21:11</StartDate>
<EndDate>2014-09-23 16:09:58</EndDate>
<Finished>1</Finished>
</Response>
</xml>
我已尝试过本网站上显示的OPENROWSET方法
http://blogs.msdn.com/b/simonince/archive/2009/04/24/flattening-xml-data-in-sql-server.aspx
使用这样的查询:
SELECT
a1.value('(RESPONSEID/text())[1]', 'varchar(50)') as RESPONSEID,
a2.value('(RESPONSESET/text())[1]', 'varchar(50)') as RESPONSESET,
a3.value('(NAME/text())[1]', 'varchar(50)') as NAME
FROM XmlSourceTable
CROSS APPLY XmlData.nodes('//Response') AS RESPONSEID(a1)
CROSS APPLY XmlData.nodes('//Response') AS RESPONSESET(a2)
CROSS APPLY XmlData.nodes('//Response') AS NAME(a3)
我让它工作了一次,但是碎片输出是重复值而不是出现在我想要的表格中,这就像下面的输出一样,但实际上注意到表格非常宽,至少有450行。另一个问题是由于宽度大于255我无法将其转换为.txt并导入它虽然我非常喜欢使用和粉碎原生XML,因此这个过程可以自动化:
RESPONSEID RESPONSESET NAME EXTERNALDATAREFERENCE EMAILADDRESS IPADDRESS STATUS STARTDATE ENDDATE
R_a4yThVvKXzVyftz Default Response Set Doe, John 1/1/2014 doej@gmail.com 123.12.123 0 9/18/2014 9:21 9/23/2014 16:09
R_06znwEis73yLsnX NonDefault Response Set Doe, Jane 1/1/2014 doeja@gmail.com 123.12.123 0 9/18/2014 5:29 9/29/2014 9:42
R_50HuB0jDFfI6hmZ Response Set 1 Doe, Cindy 1/1/2014 doec@gmail.com 123.12.123 0 9/18/2014 17:21 10/1/2014 11:45
我找到了这个应用程序
https://www.novixys.com/ExultSQLServer/
除了响应表之外,还为每个为响应表创建一个表的XML文件粉碎了XML文件,它为每个响应节点创建了一个表,从而产生了大约500个额外的表。此外,该应用程序的成本为250美元..
答案 0 :(得分:1)
您无需为要提取的每个值添加交叉申请。一个就够了。
SELECT
R.X.value('(ResponseID/text())[1]', 'varchar(50)') as RESPONSEID,
R.X.value('(ResponseSet/text())[1]', 'varchar(50)') as RESPONSESET,
R.X.value('(Name/text())[1]', 'varchar(50)') as NAME
FROM XmlSourceTable
CROSS APPLY XmlData.nodes('//Response') AS R(X)