使用xslt进行多级分组的节点:如何在输出中隐藏父节点?

时间:2019-05-11 12:53:49

标签: xml xslt xslt-1.0

我有以下XML:

<?xml version = "1.0" encoding="windows-1251"?>

<PLANTS>
    <PLANT>
        <NAME>APPLE</NAME>
        <SIZE>SMALL</SIZE>
        <TYPE>FRUIT</TYPE>
    </PLANT>
    <PLANT>
        <NAME>CUCUMBER</NAME>
        <SIZE>SMALL</SIZE>
        <TYPE>VEGETABLE</TYPE>
    </PLANT>
    <PLANT>
        <NAME>WATERMELON</NAME>
        <SIZE>BIG</SIZE>
        <TYPE>FRUIT</TYPE>
    </PLANT>
     <PLANT>
        <NAME>ORANGE</NAME>
        <SIZE>SMALL</SIZE>
        <TYPE>FRUIT</TYPE>
    </PLANT>
    <PLANT>
        <NAME>CARROT</NAME>
        <SIZE>SMALL</SIZE>
        <TYPE>VEGETABLE</TYPE>
    </PLANT>
</PLANTS>

我想将此数据表示为HTML表,按类型分组,然后按大小分组。 到目前为止,我已经有了这个XSLT代码(使用xslt-1.0对我来说是必须的):

<xsl:stylesheet version="1.0" xmlns:xsl="http://www.w3.org/1999/XSL/Transform" xmlns:cfg="http://tempuri.org/config" exclude-result-prefixes="cfg">
   <xsl:output method="html" indent="yes"/>
   <xsl:key name="Type" match="PLANT" use="TYPE"/>
   <xsl:key name="TypeSize" match="PLANT" use="concat(TYPE, '|', SIZE)"/>

   <xsl:template match="PLANTS">
      <xsl:copy>
          <xsl:apply-templates mode="type" select="PLANT[generate-id() = generate-id(key('Type', TYPE)[1])]">
            <xsl:sort select="TYPE" />
         </xsl:apply-templates>
      </xsl:copy>
   </xsl:template>
   <xsl:template match="PLANT" mode="type">

      <xsl:variable name="type" select="TYPE"/>
      <table>
         <tbody>
            <tr>
               <td >TYPE :
                  <xsl:value-of select="$type"/></td>
            </tr>
            <xsl:apply-templates mode="typeSize" select="key('Type', $type)[generate-id()  = generate-id(key('TypeSize',concat(TYPE, '|', SIZE))[1])]"/>
         </tbody>
      </table>
   </xsl:template>


   <xsl:template match="PLANT" mode="typeSize">
      <xsl:variable name="typeSize" select="concat(TYPE, '|', SIZE)"/>
      <tr>
         <td >SIZE :
            <xsl:value-of select="SIZE"/></td>
      </tr>
      <xsl:for-each select="key('TypeSize',$typeSize)">
         <tr>
            <td>
               <xsl:value-of select="NAME"/>
            </td>

         </tr>
      </xsl:for-each>
   </xsl:template>

   <xsl:template match="PLANT">
      <xsl:copy-of select="."/>
   </xsl:template>
</xsl:stylesheet>

所以输出是:

<PLANTS>
   <table>
      <tbody>
         <tr>
            <td>TYPE :
               FRUIT
            </td>
         </tr>
         <tr>
            <td>SIZE :
               SMALL
            </td>
         </tr>
         <tr>
            <td>APPLE</td>
         </tr>
         <tr>
            <td>ORANGE</td>
         </tr>
         <tr>
            <td>SIZE :
               BIG
            </td>
         </tr>
         <tr>
            <td>WATERMELON</td>
         </tr>
      </tbody>
   </table>
   <table>
      <tbody>
         <tr>
            <td>TYPE :
               VEGETABLE
            </td>
         </tr>
         <tr>
            <td>SIZE :
               SMALL
            </td>
         </tr>
         <tr>
            <td>CUCUMBER</td>
         </tr>
         <tr>
            <td>CARROT</td>
         </tr>
      </tbody>
   </table>
</PLANTS>

输出几乎是完美的,但是我想摆脱这个<PLANTS>标签。我该怎么办?

您可以找到所有代码here

1 个答案:

答案 0 :(得分:1)

您在其中创建

<xsl:template match="PLANTS">
  <xsl:copy>

因此只需删除该xsl:copy并仅应用模板(或设置一些HTML文档结构,前提是您说要HTML输出)。