1

这个问题中,我询问是否可以使用 XSLT 防止输出连续的相同值。在这个问题中,我扩展了输入数据,以便XSLT 1.0 语法的Muenchian 分组方法更加清晰。

是否可以使用 XSL 转换仅匹配 XML 文档中第一次出现的值?

我想打印出 f2,f3 中的每个值,但只打印 f1 内容的第一个实例,保留顺序。

XML 数据

    <doc> 
    <datum>
        <f1>One</f1>
        <f2>Monday</f2>
        <f3>January</f3>
      </datum>
      <datum>
        <f1>One</f1>
        <f2>Tuesday</f2>
        <f3>February</f3>
      </datum>
      <datum>
        <f1>Two</f1>
        <f2>Wednesday</f2>
        <f3>March</f3>
    </datum>
    </doc>

输出

      One
      -Monday-January
      -Tuesday-February
      Two
      -Wednesday-March

这是 Dimitre Novatchev 针对包含字段 f1 和 f2 的输入数据集为 XSLT 1.0 提出的解决方案。

<xsl:stylesheet version="1.0" xmlns:xsl="http://www.w3.org/1999/XSL/Transform">
 <xsl:output method="text"/>

 <xsl:key name="kDatumByF1" match="datum" use="f1"/>

 <xsl:template match=
   "datum[generate-id() = generate-id(key('kDatumByF1', f1)[1])]">
   <xsl:value-of select="concat('&#xA;', f1)"/>
   <xsl:apply-templates select="key('kDatumByF1', f1)/f2" mode="inGroup"/>
 </xsl:template>

 <xsl:template match="f2" mode="inGroup">
   - <xsl:value-of select="."/>
 </xsl:template>
 <xsl:template match="text()"/>
</xsl:stylesheet>

它工作得很好,但我不确定要扩展以在输出中包含字段“f3”的语法。

4

2 回答 2

2
<xsl:stylesheet version="1.0" xmlns:xsl="http://www.w3.org/1999/XSL/Transform">
 <xsl:output method="text"/>

 <xsl:key name="kDatumByF1" match="datum" use="f1"/>

 <xsl:template match=
   "datum[generate-id() = generate-id(key('kDatumByF1', f1)[1])]">
   <xsl:value-of select="concat('&#xA;', f1)"/>
   <xsl:apply-templates select="key('kDatumByF1', f1)/*[self::f2 | self::f3]" mode="inGroup"/>
 </xsl:template>

 <xsl:template match="f2" mode="inGroup">
   - <xsl:value-of select="."/>
 </xsl:template>

 <xsl:template match="f3" mode="inGroup">
  <xsl:value-of select="concat('-',.)"/>
 </xsl:template>

 <xsl:template match="text()"/>
</xsl:stylesheet>
于 2012-08-15T03:33:28.037 回答
1

这种转变

<xsl:stylesheet version="1.0" xmlns:xsl="http://www.w3.org/1999/XSL/Transform">
     <xsl:output method="text"/>
     <xsl:strip-space elements="*"/>
     <xsl:key name="kDatumByF1" match="datum" use="f1"/>

     <xsl:template match=
       "datum[generate-id() = generate-id(key('kDatumByF1', f1)[1])]">
       <xsl:value-of select="concat(f1, '&#xA;')"/>
       <xsl:apply-templates mode="inGroup"
           select="key('kDatumByF1', f1)/*[self::f2 or self::f3]" />
     </xsl:template>

     <xsl:template match="f2|f3" mode="inGroup">
       <xsl:value-of select="concat('- ',., ' ')"/>
       <xsl:if test="not(following-sibling::*[self::f2 or self::f3])">
        <xsl:text>&#xA;</xsl:text>
       </xsl:if>
     </xsl:template>
     <xsl:template match="text()"/>
</xsl:stylesheet>

应用于提供的 XML 文档时

<doc>
    <datum>
        <f1>One</f1>
        <f2>Monday</f2>
        <f3>January</f3>
    </datum>
    <datum>
        <f1>One</f1>
        <f2>Tuesday</f2>
        <f3>February</f3>
    </datum>
    <datum>
        <f1>Two</f1>
        <f2>Wednesday</f2>
        <f3>March</f3>
    </datum>
</doc>

产生想要的正确结果

One
- Monday - January 
- Tuesday - February 
Two
- Wednesday - March 

说明

正确使用孟池分组法

请注意

即使可以按任何顺序出现,f2该解决方案也会产生想要的结果。f3

于 2012-08-15T03:44:06.680 回答