获取xslt 2.0中每5个字符的最大元素出现次数

时间:2018-07-17 04:07:17

标签: xslt xslt-2.0

我需要每5个字符获得该元素的最大迭代次数(例如15次迭代)。例如,我下面有一个xml文件:

输入文件:

<Record>
<AAA>1DFAHSDJFOHR79324325Y49HRFDSHFADSLFJOSDHFDFASNDFAEJRO3U023U4EWR3454433FGSDG46244SDG6409876</AAA>
</Record>

期望的输出:

<Record>
<Data>1DFAH</Data>
<Data>SDJFO</Data>
<Data>HR793</Data>
<Data>24325</Data>
<Data>Y49HR</Data>
<Data>FDSHF</Data>
<Data>ADSLF</Data>
<Data>JOSDH</Data>
<Data>FDFAS</Data>
<Data>NDFAE</Data>
<Data>JRO3U</Data>
<Data>023U4</Data>
<Data>EWR34</Data>
<Data>54433</Data>
<Data>FGSDG</Data>
</Record>

XSLT代码:

<xsl:stylesheet version="2.0" xmlns:xsl="http://www.w3.org/1999/XSL/Transform" xmlns:xs="http://www.w3.org/2001/XMLSchema" xmlns:fn="http://www.w3.org/2005/xpath-functions">
<xsl:output method="xml" version="1.0" encoding="UTF-8" indent="yes"/>
<xsl:template match="AAA">
<Record>
    <xsl:analyze-string regex=".{{5}}" select=".">
        <xsl:matching-substring>
            <Data>
                <xsl:value-of select="."/>
            </Data>
        </xsl:matching-substring>
        <xsl:non-matching-substring>
            <Data>
                <xsl:value-of select="."/>
            </Data>
        </xsl:non-matching-substring>
    </xsl:analyze-string>   
</Record>
</xsl:template>

我只需要获取直到Data的第15次迭代的值,而忽略多余的值。如何在我的xslt中做到这一点?

谢谢。

3 个答案:

答案 0 :(得分:0)

尝试一下:

<xsl:stylesheet version="2.0" xmlns:xsl="http://www.w3.org/1999/XSL/Transform" xmlns:xs="http://www.w3.org/2001/XMLSchema" xmlns:fn="http://www.w3.org/2005/xpath-functions">
    <xsl:output method="xml" version="1.0" encoding="UTF-8" indent="yes"/>
    <xsl:template match="AAA">
        <Record>
            <!-- Assing all in a Variable -->
            <xsl:variable name="DATA">
            <xsl:analyze-string regex=".{{5}}" select=".">
                <xsl:matching-substring>
                    <Data>
                        <xsl:value-of select="."/>
                    </Data>
                </xsl:matching-substring>
                <xsl:non-matching-substring>
                    <Data>
                        <xsl:value-of select="."/>
                    </Data>
                </xsl:non-matching-substring>
            </xsl:analyze-string>   
            </xsl:variable>
            <!-- Copy only first Fifteen Occurances -->
            <xsl:copy-of select="$DATA//Data[position() lt 16]"/>
        </Record>
    </xsl:template>
</xsl:stylesheet>

输出

<Record>
   <Data>1DFAH</Data>
   <Data>SDJFO</Data>
   <Data>HR793</Data>
   <Data>24325</Data>
   <Data>Y49HR</Data>
   <Data>FDSHF</Data>
   <Data>ADSLF</Data>
   <Data>JOSDH</Data>
   <Data>FDFAS</Data>
   <Data>NDFAE</Data>
   <Data>JRO3U</Data>
   <Data>023U4</Data>
   <Data>EWR34</Data>
   <Data>54433</Data>
   <Data>FGSDG</Data>
</Record>

答案 1 :(得分:0)

进一步扩展解决方案,您可以将analyze-string的输出存储到变量splitArray中。

<xsl:variable name="strValue" select="AAA" />
<xsl:variable name="splitArray">
    <xsl:analyze-string regex=".{{5}}" select="$strValue">
        <xsl:matching-substring>
            <Data><xsl:value-of select="."/></Data>
        </xsl:matching-substring>
        <xsl:non-matching-substring>
            <Data><xsl:value-of select="."/></Data>
        </xsl:non-matching-substring>
    </xsl:analyze-string>
</xsl:variable>

在变量上添加一个for-each循环,该循环将提取存储数组的前15个索引

<xsl:for-each select="$splitArray/Data[position() &lt; 16]">
    <Data><xsl:value-of select="." /></Data>
</xsl:for-each>

下面是完整的XSLT供您参考。

<xsl:stylesheet version="2.0" xmlns:xsl="http://www.w3.org/1999/XSL/Transform">
    <xsl:output method="xml" indent="yes" />
    <xsl:strip-space elements="*" />
    <xsl:template match="Record">
        <xsl:copy>
            <xsl:variable name="strValue" select="AAA" />
            <xsl:variable name="splitArray">
                <xsl:analyze-string regex=".{{5}}" select="$strValue">
                    <xsl:matching-substring>
                        <Data><xsl:value-of select="."/></Data>
                    </xsl:matching-substring>
                    <xsl:non-matching-substring>
                        <Data><xsl:value-of select="."/></Data>
                    </xsl:non-matching-substring>
                </xsl:analyze-string>
            </xsl:variable>
            <xsl:for-each select="$splitArray/Data[position() &lt; 16]">
                <Data><xsl:value-of select="." /></Data>
            </xsl:for-each>
        </xsl:copy>
    </xsl:template>
</xsl:stylesheet>

输出

<Record>
   <Data>1DFAH</Data>
   <Data>SDJFO</Data>
   <Data>HR793</Data>
   <Data>24325</Data>
   <Data>Y49HR</Data>
   <Data>FDSHF</Data>
   <Data>ADSLF</Data>
   <Data>JOSDH</Data>
   <Data>FDFAS</Data>
   <Data>NDFAE</Data>
   <Data>JRO3U</Data>
   <Data>023U4</Data>
   <Data>EWR34</Data>
   <Data>54433</Data>
   <Data>FGSDG</Data>
</Record>

analyze-string的另一种选择是使用XSLT 2.0的idiv功能将字符串分成5个字符的块。

<xsl:variable name="splitArray">
    <xsl:for-each select="0 to string-length($strValue) idiv 5">
        <Data>
            <xsl:value-of select="substring($strValue, . * 5 + 1, 5)" />
        </Data>
    </xsl:for-each>
</xsl:variable>

希望这会有所帮助。

答案 2 :(得分:0)

我看不到如何获得不匹配的字符串。至于前15个匹配项,position()是可用的,请参见https://www.w3.org/TR/xslt20/#element-matching-substring解释:“子字符串在匹配和不匹配子字符串序列中的位置将是上下文位置”。因此您可以检查它:

<xsl:template match="AAA">
    <Record>
        <xsl:analyze-string regex=".{{5}}" select=".">
            <xsl:matching-substring>
              <xsl:if test="position() le 15">
                <Data>
                    <xsl:value-of select="."/>
                </Data>
              </xsl:if>
            </xsl:matching-substring>            
        </xsl:analyze-string>   
    </Record>
</xsl:template>

https://xsltfiddle.liberty-development.net/nc4NzQv/2