1

我有一个需要上传到 SQL 表中的示例 xml 文件。

xml 文件下方是用于选择要插入到表中的 XML 值的 SQL 查询

问题:我无法获得这些<Actual>,<ExpectedValue>值,因为它们不止一次出现

如果有人可以帮助纠正/指导我获得正确的价值观,将不胜感激

谢谢。

<?xml version="1.0" encoding="utf-8" ?>
<Results>
    <General>
        <Version>1.01</Version>
        <InputFilename>TestFile.xml</InputFilename>
        <Filename>xyz.XML</Filename>
        </General>
    <Tests>
        <Test Name="Test 1">
            <Number>0</Number>
            <MinimumSampleCount>1</MinimumSampleCount>
            <ExpectedValues>
            <ExpectedValue>8</ExpectedValue>
            <ExpectedValue>5</ExpectedValue>
            </ExpectedValues>
            <Actual>
                <seq>1</seq>
                <ValueFound>8</ValueFound>
                <seqTestResult>Passed</seqTestResult>
            </Actual>
            <Actual>
                <seq>3</seq>
                <ValueFound>8</ValueFound>
                <seqTestResult>Passed</seqTestResult>
            </Actual>
            <Result>Last sequence matches test cases.</Result>
            <TestResult>Passed</TestResult>
            </Test>
        <Test Name="Test 3">
            <Number>25</Number>
            <ExpectedValues><ExpectedValue>3.50</ExpectedValue>
            <ExpectedValue>3.56</ExpectedValue>
            <ExpectedValue>3.60</ExpectedValue>
            </ExpectedValues>
            <Result>not applicable</Result>
            <TestResult>Skipped</TestResult>
        </Test>
        <OverallTestResult>Passed</OverallTestResult>
    </Tests>
</Results>

SQL 代码:

INSERT INTO dbo.Results_XML ([Version],[InputFilename],[Filename],
      [OverallTestResult],Name,Number,MinimumSampleCount,ActualNumberOfSamples,ExpectedValue,
       ActualSeq, ActualValueFound,ActualseqTestResult,CompareValue,Result,TestResult

    SELECT [Version] = x.data.value('Version[1]','numeric(3,2)'),
       [InputFilename] = x.data.value('InputFilename[1]','varchar(80)'),
       [Filename] = x.data.value('Filename[1]','varchar(80)'),
       [OverallTestResult]=T2.N.value('OverallTestResult[1]','varchar(15)'),
       [Test Name]= y.data.value('@Name','varchar(255)')
         ,[Number]= y.data.value('Number[1]','int'),
         [MinimumSampleCount]=y.data.value('Number[1]','int'),
         [ActualNumberOfSamples]=y.data.value('ActualNumberOfSamples[1]','int')
         ,[ExpectedValue]=z.data.value('ExpectedValue[1]','varchar(255)')
         ,[ActualSeq]=v.data.value('Seq[1]','int'),
         ,ActualValueFound=v.data.value('ValueFound[1]','int'),
         ,ActualseqTestResult=v.data.value('seqTestResult[1]','varchar(255)'),
        ,[CompareValue]=y.data.value('CompareValue[1]','bigint')
         ,[Result]=y.data.value('Result[1]','varchar(40)'),
         [TestResult]=y.data.value('TestResult[1]','varchar(10)')

    FROM CD t
       CROSS APPLY t.XMLData.nodes('/Results/General') x(data)
       cross apply t.XMLData.nodes('/Results/Tests') as T2(N)
       CROSS APPLY t.XMLData.nodes('/Results/Tests/Test') as y(data) 
       CROSS APPLY t.XMLData.nodes('Test/ExpectedValues/Expected') z(data) 
       CROSS APPLY t.XMLData.nodes('Test/ExpectedValues/Actual/') v(data)
4

1 回答 1

0

我假设(基于您之前的问题)这是针对SQL Server的- 对吗?
您应该始终明确明确地指定您正在使用的数据库系统 - 习惯它!

你需要使用这样的东西:

  • 获取XML节点供<Results>/<General>节点获取一些基本数据
  • 然后获取所有<Test>节点的列表 - 从那里获取一些数据
  • 基于每个<Test>节点 - 获取它的<ExpectedValues>/<ExpectedValue>节点列表以及其中的<Actual>节点<Test>并挑选出您需要的数据

以我的经验,使用描述性名称是一个好主意- useGeneralData等,ExpectedData而不仅仅是x,yz- 这样更容易理解您正在处理的内容!

这是我使用的 T-SQL / XQuery 语句:

SELECT 
    -- General values
    [Version] = GeneralData.value('Version[1]','numeric(3,2)'),
    [InputFilename] = GeneralData.value('InputFilename[1]','varchar(80)'),
    [Filename] = GeneralData.value('Filename[1]','varchar(80)'),
    -- Test-specific values
    [Test Name]= TestData.value('@Name','varchar(255)'),
    [Test Number]= TestData.value('Number[1]','int'),
    -- Test-specific expected values
    [ExpectedValue] = ExpectedData.value('.', 'varchar(255)'),
    -- Test-specific actual values
    [ActualSeq] = ActualData.value('(seq)[1]', 'int'),
    ActualValueFound = ActualData.value('(ValueFound)[1]', 'int'),
    ActualseqTestResult = ActualData.value('(seqTestResult)[1]', 'varchar(255)')
FROM 
    CD t
CROSS APPLY
    -- fetch the <Results> / <General> node
    XMLdata.nodes('/Results/General') AS XGD(GeneralData)
CROSS APPLY
    -- fetch a list of  <Results> / <Tests> / <Test> nodes
    XMLDATA.nodes('/Results/Tests/Test') AS XTD(TestData)
CROSS APPLY
    -- for each <Test> node - fetch its contained <ExpectedValues>/<ExpectedValue> nodes
    TestData.nodes('ExpectedValues/ExpectedValue') AS XED(ExpectedData)
CROSS APPLY
    -- for each <Test> node - fetch its contained <Actual> nodes
    TestData.nodes('Actual') AS XAD(ActualData)
于 2013-03-20T06:36:39.950 回答