OPENXML从XML中提取数据并添加到表中

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

标签: sql openxml

我有一个XML文件,我想从中获取数据并将其放入SQL表中。我的问题是在同一个XML文件中路径不同。

例如,

一条路径= 'root/DescriptorRecord/DescriptorName'

第二条路径= 'root/DescriptorRecord/ConceptList/Concept/TermList/Term'

我不知道如何从同一XML中的两个不同路径获取值。

以下是我的XML:

<root>
<DescriptorRecord DescriptorClass = "1">
  <DescriptorName>
   <String>abc</String>
  </DescriptorName>
  <ConceptList>
   <Concept PreferredConceptYN="Y">
    <TermList>
     <Term  ConceptPreferredTermYN="Y"  IsPermutedTermYN="N"  LexicalTag="NON"  PrintFlagYN="Y"  RecordPreferredTermYN="Y">
        <String>abc</String>
     </Term>
     <Term  ConceptPreferredTermYN="N"  IsPermutedTermYN="N"  LexicalTag="NON"  PrintFlagYN="N"  RecordPreferredTermYN="N">
        <String>pqr</String>
     </Term>
     <Term  ConceptPreferredTermYN="N"  IsPermutedTermYN="N"  LexicalTag="NON"  PrintFlagYN="Y"  RecordPreferredTermYN="N">
        <String>xyz</String>
    </Term>
   </TermList>
   </Concept>
  </ConceptList>
 </DescriptorRecord>
 <DescriptorRecord DescriptorClass = "1">
  <DescriptorName>
   <String>Numerics</String>
  </DescriptorName>
  <ConceptList>
   <Concept PreferredConceptYN="Y">
    <TermList>
     <Term  ConceptPreferredTermYN="Y"  IsPermutedTermYN="N"  LexicalTag="NON"  PrintFlagYN="Y"  RecordPreferredTermYN="Y">
        <String>123</String>
     </Term>
     <Term  ConceptPreferredTermYN="N"  IsPermutedTermYN="N"  LexicalTag="NON"  PrintFlagYN="N"  RecordPreferredTermYN="N">
        <String>456</String>
     </Term>
     <Term  ConceptPreferredTermYN="N"  IsPermutedTermYN="N"  LexicalTag="NON"  PrintFlagYN="Y"  RecordPreferredTermYN="N">
        <String>789</String>
    </Term>
   </TermList>
   </Concept>
  </ConceptList>
 </DescriptorRecord>
 </root>

我的SQL查询:

DECLARE @XML AS XML, @hDoc AS INT, @SQL NVARCHAR (MAX)

SELECT @XML = XMLData FROM XMLwithOpenXML

EXEC sp_xml_preparedocument @hDoc OUTPUT, @XML

SELECT Descriptor, Terms
FROM OPENXML(@hDoc, 'root/DescriptorRecord/DescriptorName')
WITH 
(
 Descriptor [varchar](100) 'String',
 Terms [varchar](100) 'String'
)

  SELECT Terms
  FROM OPENXML(@hDoc, 'root/DescriptorRecord/ConceptList/Concept/TermList/Term')
  WITH 
  (
    Descriptor [varchar](100) 'String'
    Terms [varchar](100) 'String'
  )

EXEC sp_xml_removedocument @hDoc
GO

结果:

http://imgur.com/wvS1pNL,JpApXuQ

预期结果

http://imgur.com/wvS1pNL,JpApXuQ#1

1 个答案:

答案 0 :(得分:0)

因此,在变量中设置样本:

DECLARE @X XML =  N'<root>
<DescriptorRecord DescriptorClass = "1">
  <DescriptorName>
   <String>abc</String>
  </DescriptorName>
  <ConceptList>
   <Concept PreferredConceptYN="Y">
    <TermList>
     <Term  ConceptPreferredTermYN="Y"  IsPermutedTermYN="N"  LexicalTag="NON"  PrintFlagYN="Y"  RecordPreferredTermYN="Y">
        <String>abc</String>
     </Term>
     <Term  ConceptPreferredTermYN="N"  IsPermutedTermYN="N"  LexicalTag="NON"  PrintFlagYN="N"  RecordPreferredTermYN="N">
        <String>pqr</String>
     </Term>
     <Term  ConceptPreferredTermYN="N"  IsPermutedTermYN="N"  LexicalTag="NON"  PrintFlagYN="Y"  RecordPreferredTermYN="N">
        <String>xyz</String>
    </Term>
   </TermList>
   </Concept>
  </ConceptList>
 </DescriptorRecord>
 <DescriptorRecord DescriptorClass = "1">
  <DescriptorName>
   <String>Numerics</String>
  </DescriptorName>
  <ConceptList>
   <Concept PreferredConceptYN="Y">
    <TermList>
     <Term  ConceptPreferredTermYN="Y"  IsPermutedTermYN="N"  LexicalTag="NON"  PrintFlagYN="Y"  RecordPreferredTermYN="Y">
        <String>123</String>
     </Term>
     <Term  ConceptPreferredTermYN="N"  IsPermutedTermYN="N"  LexicalTag="NON"  PrintFlagYN="N"  RecordPreferredTermYN="N">
        <String>456</String>
     </Term>
     <Term  ConceptPreferredTermYN="N"  IsPermutedTermYN="N"  LexicalTag="NON"  PrintFlagYN="Y"  RecordPreferredTermYN="N">
        <String>789</String>
    </Term>
   </TermList>
   </Concept>
  </ConceptList>
 </DescriptorRecord>
 </root>'

您希望首先在内部查询中选择描述符,并将结果返回到外部查询,您可以在第二个.nodes()调用中将描述符列用作xpath条件。像这样:

SELECT Descriptor.Data.value('./DescriptorName[1]/String[1]','nvarchar(200)') AS Descriptor, Terms.Data.value('.','nvarchar(200)') AS Terms
FROM @x.nodes('root/DescriptorRecord') Descriptor(Data)
    cross apply Descriptor.Data.nodes('./ConceptList/Concept/TermList/Term/String') Terms(Data)

编辑:试图降低计算成本。