XSL - 将子节点提升为父节点和distinct-value

时间:2017-03-29 10:49:58

标签: xml xslt xslt-2.0 saxon

我有一个xml文件,其中包含父元素而不是子元素,其中子元素应该是父元素。这是一个例子:

<root>
 <sub-area number="1">
  <name>West Viking</name>
  <condition>good</condition>
  <area>
   <name>Viking</name>
   <condition>average</condition>
  <area>
 </sub-area>
 <sub-area number="2">
  <name>East Viking</name>
  <condition>good</condition>
  <area>
   <name>Viking</name>
   <condition>average</condition>
  <area>
 </sub-area>
 <sub-area number="3">
  <name>North Viking, South Viking</name>
  <condition>good</condition>
  <area>
   <name>Viking</name>
   <condition>average</condition>
  <area>
 </sub-area>
 <sub-area number="4">
  <name>West Utshire</name>
  <condition>good</condition>
  <area>
   <name>Utshire</name>
   <condition>good</condition>
  <area>
 </sub-area>
 <sub-area number="5">
  <name>East Utshire</name>
  <condition>good</condition>
  <area>
   <name>Utshire</name>
   <condition>good</condition>
  <area>
 </sub-area>
 <sub-area number="6">
  <name>North Utshire, South Utshire</name>
  <condition>average/condition>
  <area>
   <name>Utshire</name>
   <condition>good</condition>
  <area>
 </sub-area>
</root>

我希望通过子区域作为该区域的子节点来简化本文档。例如:

<root>
 <area name="Viking">
  <condition>average</condition>
  <sub-area name="West Viking">
   <condition>good</condition>
  </sub-area>
  <condition>average</condition>
  <sub-area name="East Viking">
   <condition>bad</condition>
  </sub-area>
  <condition>average</condition>
  <sub-area name="North Viking">
   <condition>average</condition>
  </sub-area>
  <sub-area name="South Viking">
   <condition>good</condition>
  </sub-area>
 </area>
 <area name="Utshire">
  <condition>good</condition>
  <sub-area name="West Utshire">
   <condition>good</condition>
  </sub-area>
  <condition>average</condition>
  <sub-area name="East Utshire">
   <condition>bad</condition>
  </sub-area>
  <condition>average</condition>
  <sub-area name="North Utshire">
   <condition>good</condition>
  </sub-area>
  <sub-area name="South Utshire">
   <condition>good</condition>
 </area>
</root>

到目前为止,我所尝试的一切都失败了。看着doc和论坛,我找不到任何东西。我不知道如何处理这个问题。谢谢你的帮助。

1 个答案:

答案 0 :(得分:0)

第一件事是将源XML带到适当的形状:

  • 在结束area代码中添加“/”,
  • /condition>更改为</condition>(在1个位置)。

现在回到主营业务:

  • sub-area上的area/name标签开始。
  • 然后为每个区域名称创建父级(area)标记。
  • 在此区域内放置sub-area标签 - 当前组的内容。

这是一个完整的解决方案:

<?xml version="1.0" encoding="UTF-8" ?>
<xsl:transform xmlns:xsl="http://www.w3.org/1999/XSL/Transform" version="2.0">
  <xsl:output method="xml" omit-xml-declaration="yes" encoding="UTF-8" indent="yes" />

  <xsl:template match="root">
    <xsl:copy>
      <xsl:for-each-group select="sub-area" group-by="area/name">
        <xsl:element name="area">
          <xsl:attribute name="name" select="current-grouping-key()"/>
          <xsl:sequence select="area/condition"/>
          <xsl:for-each select="current-group()">
            <xsl:element name="sub-area">
              <xsl:attribute name="name" select="name"/>
              <xsl:sequence select="condition"/>
            </xsl:element>
          </xsl:for-each>
        </xsl:element>
      </xsl:for-each-group>
    </xsl:copy>
  </xsl:template>
</xsl:transform>