为它的每个后代形成多个父节点

Form multiple parent node for each of its descendants

我对 xslt 还很陌生,对这个问题感到很头疼。谁能帮我解决这个问题? 请找到输入 XML,我需要在 L 节点的 id 字段中查找文本 L1 并搜索 sublocation id 和 pit ref 具有文本 L1 并形成新的 L1 节点并在每个 L1 节点下安排 sublocation 和 pit。

<root>
  <L Id="L1">
    <test>ed</test>
    <SubLocation id="L1S1">
      <check>
        <AId>1</AId>
      </check>
      <MD>
        <UnitNumber>1</UnitNumber>
      </MD>
    </SubLocation>
    <SubLocation id="L1S2">
      <check>
        <AId>2</AId>
      </check>
      <MD>
        <UnitNumber>2</UnitNumber>
      </MD>
    </SubLocation>
  </L>
  <L Id="L2">
    <test>ed</test>
    <SubLocation id="L2S1">
      <check>
        <AId>1</AId>
      </check>
      <MD>
        <UnitNumber>1</UnitNumber>
      </MD>
    </SubLocation>
    <SubLocation id="L2S2">
      <check>
        <AId>2</AId>
      </check>
      <MD>
        <UnitNumber>2</UnitNumber>
      </MD>
    </SubLocation>
  </L>
  <cp>
    <current>
      <Amt>20154.00</Amt>
    </current>
    <pi>
      <pit ref="L1S1">
        <value>1232</value>
      </pit>
      <pit ref="L1S2">
        <value>12345</value>
      </pit>
      <pit ref="L1S3">
        <value>12387</value>
      </pit>
      <pit ref="L2S1">
        <value>1232</value>
      </pit>
      <pit ref="L2S2">
        <value>12345</value>
      </pit>
    </pi>
  </cp>
</root>

我需要以下格式的o/p

<root>
  <L1>
    <SubLocation id="L1S1">
      <check>
        <AId>1</AId>
      </check>
      <MD>
        <UnitNumber>1</UnitNumber>
      </MD>
    </SubLocation>
    <pit ref="L1S1">
      <value>1232</value>
    </pit>
  </L1>
  <L1>
    <SubLocation id="L1S2">
      <check>
        <AId>2</AId>
      </check>
      <MD>
        <UnitNumber>2</UnitNumber>
      </MD>
    </SubLocation>
    <pit ref="L1S2">
      <value>12345</value>
    </pit>
  </L1>
  <L2>
    <SubLocation id="L2S1">
      <check>
        <AId>1</AId>
      </check>
      <MD>
        <UnitNumber>1</UnitNumber>
      </MD>
    </SubLocation>
    <pit ref="L2S1">
      <value>1232</value>
    </pit>
  </L2>
  <L2>
    <SubLocation id="L2S2">
      <check>
        <AId>2</AId>
      </check>
      <MD>
        <UnitNumber>2</UnitNumber>
      </MD>
    </SubLocation>
    <pit ref="L2S2">
      <value>12345</value>
    </pit>
  </L2>
</root>

这是我的 xslt

<xsl:stylesheet version="1.0" xmlns:xsl="http://www.w3.org/1999/XSL/Transform">
  <xsl:output indent="yes"/>
  <xsl:strip-space elements="*"/>
  <xsl:key name="cpbyid" match="pit" use="@ref"/>
  <xsl:key name="slById" match="SubLocation" use="@id"/>
  <xsl:key name="locbyId" match="L" use="@id"/>

  <xsl:template match="@*|node()" name="identity">
    <xsl:copy>
      <xsl:apply-templates select="@*|node()"/>
    </xsl:copy>
  </xsl:template>

  <xsl:template match="L/*[@id]">
    <L>
      <xsl:value-of select="//L/@id"/>
    <pifo>
      <xsl:call-template name="subloc"></xsl:call-template>    
      <xsl:call-template name="identity"/>
    </pifo>
    </L>
  </xsl:template>


  <xsl:template match="pit/*[@ref]" name="subloc">
    <inf>
      <xsl:copy-of select="key('cpbyid', @id)"/>
      <xsl:copy-of select="key('slById', @id)"/>
    </inf>
  </xsl:template> 

</xsl:stylesheet>

我不太理解你的描述,我可能遗漏了一些东西。有什么理由不能简单地做:

XSLT 1.0

<xsl:stylesheet version="1.0" 
xmlns:xsl="http://www.w3.org/1999/XSL/Transform">
<xsl:output method="xml" version="1.0" encoding="UTF-8" indent="yes"/>
<xsl:strip-space elements="*"/>

<xsl:key name="pit" match="pit" use="@ref" />

<xsl:template match="/root">
    <xsl:copy>
        <xsl:for-each select="L/SubLocation">
             <xsl:element name="{../@Id}">
                <xsl:copy-of select="."/>
                <xsl:copy-of select="key('pit', @id)"/>
              </xsl:element>
        </xsl:for-each>
    </xsl:copy>
</xsl:template>

</xsl:stylesheet>