SQL从具有相同节点名称的xml获取值

时间:2014-07-08 21:08:42

标签: sql xml sql-server-2008 xpath

我有一个在大约20秒内运行的存储过程,看起来非常无效。我想知道是否有人对如何做得更好有任何想法。

XML

<Values>
 <Required>
  <Name Type="WS">ganderson</Name>
  <Name Type="WS">mhoffmann</Name>
  <Name Type="WS">lmcswain</Name>
  <Name Type="WS">jbranham</Name>
  <Name Type="WS">gsimpson</Name>
  <Name Type="WS">jbennett</Name>
  <Name Type="WS">bdrum</Name>
  <Name Type="WS">mtrott</Name>
  <Name Type="WS">acannon</Name>
  <Name Type="WS">dgantt</Name>
  <Name Type="WS">evalone</Name>
  <Name Type="WS">flyons</Name>
  <Name Type="WS">saheavner</Name>
 </Required>
</Values>

查询

DECLARE @tab TABLE (Usernames varchar(200),xmldata xml,FNActionID int,SubscriberType varchar(max))
  INSERT INTO @tab (Usernames) 
  SELECT SUBSTRING(Active_Dir_Name,5,LEN(Active_Dir_Name)) FROM USERS WHERE LEN(ACTIVE_DIR_NAME) > 5 AND IsEnabled = 1

  UPDATE @tab
  SET xmldata = @tag 

  UPDATE @tab
  SET FNActionID = @FnActionID

 INSERT INTO @MainTable
  SELECT xmldata.value('(/Values/Required/Name[text()=sql:column("Usernames")])[1]','varchar(max)'),FNActionID
  FROM @tab
  WHERE xmldata.exist('/Values/Required/Name[text()=sql:column("Usernames")]') = 1

这里的目标是使用表用户,列actived_dir_name并使用SELECT xmldata.value在我的xml上连接它。问题是这不在同一个表中,因此我必须将两个值都放在临时表中,以便xml知道要查找的位置。

问题是,我有大约20个不同的xml条目,我正在检查不同数据库上的整个用户列,并且运行缓慢,应该如此。

这似乎是一种落后的方式。我知道代码没有意义,如果你有任何尖锐的问题让我知道,我会尽可能地回答。

2 个答案:

答案 0 :(得分:1)

首先尝试使用外部应用,然后在where子句中绑定两者。

SELECT tag.name.value('.','nvarchar(20)')
FROM @tab tab
    outer apply tab.xmldata.nodes('/Values/Required/Name') tag(name)
where tab.Usernames = tag.name.value('.','nvarchar(20)')

此外,如果它还不存在,请考虑XML Index

答案 1 :(得分:0)

从具有相同名称的节点获取差异值的另一种方法:

xmldata.value('(/Values/Required/Name/text())[1]','varchar(max)') AS name1