XSLT 2.0 - Группировка и сортировка - ‹xsl: for-each-group›

Я хочу сгруппировать сноски по fnrtoken в порядке fnlabel. все символы с fnrtoken должны быть сгруппированы вместе по метке. но если какая-либо сноска без fnlabel находится между этими сносками, тогда следует создать новую группу для этой сноски и снова создать новую группу для оставления сноски с fnlable

Вход:

<endnotes>
    <footnote fntoken="aasdf" fnrtoken="78hyyj">
        <fnlabel>2</fnlabel>
        <para></para>
    </footnote>
    <footnote fntoken="aasdf" fnrtoken="78jjjj">
        <fnlabel>1</fnlabel>
        <para></para>
    </footnote>
    <footnote fntoken="aasdf" fnrtoken="7900hj">
        <fnlabel>4</fnlabel>
        <para></para>
    </footnote>
    <footnote fntoken="aasdf">
        <fnlabel>3</fnlabel>
        <para></para>
    </footnote>
    <footnote fntoken="aasdf">
        <fnlabel>5</fnlabel>
        <para></para>
    </footnote>
</endnotes>


Output:
<footenotegrp>
    <footnote fntoken="aasdf" fnrtoken="78jjjj">
        <fnlabel>1</fnlabel>
        <para></para>
    </footnote>
    <footnote fntoken="aasdf" fnrtoken="78hyyj">
        <fnlabel>2</fnlabel>
        <para></para>
    </footnote>
</footenotegrp>
<footenotegrp>
    <footnote fntoken="aasdf">
        <fnlabel>3</fnlabel>
        <para></para>
    </footnote>
</footenotegrp>
<footenotegrp>
    <footnote fntoken="aasdf" fnrtoken="7900hj">
        <fnlabel>4</fnlabel>
        <para></para>
    </footnote>
</footenotegrp>
<footenotegrp>
    <footnote fntoken="aasdf">
        <fnlabel>5</fnlabel>
        <para></para>
    </footnote>
</footenotegrp>

person KKK    schedule 21.01.2017    source источник


Ответы (1)


Мне кажется, вы сначала хотите отсортировать, а затем хотите сгруппировать, используя group-adjacent="exists(@fnrtoken)":

<xsl:stylesheet xmlns:xsl="http://www.w3.org/1999/XSL/Transform"
    xmlns:xs="http://www.w3.org/2001/XMLSchema"
    exclude-result-prefixes="xs"
    version="2.0">

    <xsl:output indent="yes"/>

    <xsl:template match="/*">
        <root>
            <xsl:variable name="sorted" as="element(footnote)*">
                <xsl:perform-sort select="footnote">
                    <xsl:sort select="fnlabel"></xsl:sort>
                </xsl:perform-sort>
            </xsl:variable>
            <xsl:for-each-group select="$sorted" group-adjacent="exists(@fnrtoken)">
                <xsl:choose>
                    <xsl:when test="current-grouping-key()">
                        <footnotegrp>
                            <xsl:copy-of select="current-group()"/>
                        </footnotegrp>
                    </xsl:when>
                    <xsl:otherwise>
                        <xsl:for-each select="current-group()">
                            <footnotegrp>
                                <xsl:copy-of select="."/>
                            </footnotegrp>
                        </xsl:for-each>
                    </xsl:otherwise>
                </xsl:choose>
            </xsl:for-each-group>
        </root>
    </xsl:template>

</xsl:stylesheet>

Это трансформирует

<?xml version="1.0" encoding="UTF-8"?>
<endnotes>
    <footnote fntoken="aasdf" fnrtoken="78hyyj">
        <fnlabel>2</fnlabel>
        <para></para>
    </footnote>
    <footnote fntoken="aasdf" fnrtoken="78jjjj">
        <fnlabel>1</fnlabel>
        <para></para>
    </footnote>
    <footnote fntoken="aasdf" fnrtoken="7900hj">
        <fnlabel>4</fnlabel>
        <para></para>
    </footnote>
    <footnote fntoken="aasdf">
        <fnlabel>3</fnlabel>
        <para></para>
    </footnote>
    <footnote fntoken="aasdf">
        <fnlabel>5</fnlabel>
        <para></para>
    </footnote>
</endnotes>

в

<?xml version="1.0" encoding="UTF-8"?>
<root>
   <footnotegrp>
      <footnote fntoken="aasdf" fnrtoken="78jjjj">
               <fnlabel>1</fnlabel>
               <para/>
         </footnote>
      <footnote fntoken="aasdf" fnrtoken="78hyyj">
               <fnlabel>2</fnlabel>
               <para/>
         </footnote>
   </footnotegrp>
   <footnotegrp>
      <footnote fntoken="aasdf">
               <fnlabel>3</fnlabel>
               <para/>
         </footnote>
   </footnotegrp>
   <footnotegrp>
      <footnote fntoken="aasdf" fnrtoken="7900hj">
               <fnlabel>4</fnlabel>
               <para/>
         </footnote>
   </footnotegrp>
   <footnotegrp>
      <footnote fntoken="aasdf">
               <fnlabel>5</fnlabel>
               <para/>
         </footnote>
   </footnotegrp>
</root>
person Martin Honnen    schedule 21.01.2017
comment
Большое спасибо Мартин - person KKK; 23.01.2017