【问题标题】:split text with tokenize function使用标记化功能拆分文本
【发布时间】:2014-05-08 20:22:14
【问题描述】:

我正在使用 XSLT 2.0 将 XML 转换为 HTML。我试图在每 6 个字符处拆分属性值。

我的源 XML 如下所示:

<item effrg="521529577580620621623624628628631631642645" />

我当前的(失败的 XSLT)如下所示:

<xsl:analyze-string regex=".{{6}}" select="item/@effrg">
     <xsl:matching-substring><xsl:value-of select="."/></xsl:matching-substring>
     <xsl:non-matching-substring><xsl:value-of select="."/></xsl:non-matching-substring>
</xsl:analyze-string>

我想要的输出应该是:

521529 577580 620621 623624 628628 631631 642645

我在正确的轨道上吗?有人可以帮忙吗?

【问题讨论】:

  • "我当前的(失败的 XSLT)看起来像这样:" - 它在哪里?

标签: xml xslt xpath split xslt-2.0


【解决方案1】:

或者你可以这样做

<xsl:for-each-group select="string-to-codepoints($in)" 
                    group-adjacent="(position()-1) idiv 6">
  <xsl:value-of select="codepoints-to-string((current-group(), 20))"/>
</xsl:for-each-group>

【讨论】:

    【解决方案2】:

    另一种解决方案是在 for 表达式中使用 substring() 来生成数字组序列,然后使用带有空格分隔符的 string-join() 来生成所需的输出:

    <xsl:stylesheet version="2.0" xmlns:xsl="http://www.w3.org/1999/XSL/Transform">
      <xsl:output omit-xml-declaration="yes" indent="yes"/>
    
    <xsl:template match="item">
     <xsl:variable name="size" select="6"/>
     <xsl:value-of select="string-join(for $i in 0 to string-length(@effrg) div $size
                                         return substring(@effrg, $i*$size+1, $size),
                                       ' ')"/>
    </xsl:template>
    
    </xsl:stylesheet>
    

    【讨论】:

      【解决方案3】:

      由于用户在评论中询问 Internet Explorer 支持,XSLT 2.0 可能是错误的选择。

      这是一个 XSLT 1.0 解决方案:

      <xsl:template name="splitString">
          <xsl:param name="string"/>
          <xsl:param name="size"/>
          <xsl:choose>
              <xsl:when test="string-length($string) > $size">
                  <xsl:variable name="rest">
                      <xsl:call-template name="splitString">
                          <xsl:with-param name="string" select="substring($string,$size + 1)"/>
                          <xsl:with-param name="size" select="$size"/>
                      </xsl:call-template>
                  </xsl:variable>
                  <xsl:value-of select="concat(substring($string,1,$size),' ',$rest)"/>
              </xsl:when>
              <xsl:otherwise>
                  <xsl:value-of select="$string"/>
              </xsl:otherwise>
          </xsl:choose>
      </xsl:template>
      

      可以这样调用:

      <xsl:call-template name="splitString">
          <xsl:with-param name="string" select="item/@effrg"/>
          <xsl:with-param name="size">6</xsl:with-param>
      </xsl:call-template>
      

      同样使用 XSLT-2.0 中的分析字符串,实际上这已经足够了:

      <xsl:analyze-string select="item/@effrg" regex=".{{6}}">
          <xsl:matching-substring><xsl:value-of select=".,''"/></xsl:matching-substring>
      </xsl:analyze-string>
      

      【讨论】:

      • 太棒了!谢谢。 XSLT 1.0 解决方案适用于我正在做的事情。我不知道浏览器还没有使用 XSLT 2.0。
      【解决方案4】:

      要拆分您提供的源字符串,您可以使用更简单的表达式:

      <xsl:value-of select="replace(item/@effrg, '(.{6}){7}', '$1 $2 $3 $4 $5 $6 $7')" />
      

      在你运行&lt;xsl:analyze-string&gt;的上下文中。

      使用&lt;xsl:analyze-string&gt;,您可以使用regex-group(n) 获取每个$n 组。然后,您可以在 XSLT 中循环连接递归调用模板中的空格。

      但您也可以在 XPath 2.0 中使用forstring-join 更简洁地循环以获得所需的结果:

      <xsl:template match="item">
          <xsl:variable name="size" select="floor(string-length(@effrg) div 6)"></xsl:variable>
          <xsl:analyze-string regex="(.{{6}}){{{$size}}}" select="@effrg">
              <xsl:matching-substring>
                  <xsl:value-of select="string-join(for $group in 1 to $size return regex-group($group), ' ')"/>
              </xsl:matching-substring>
          </xsl:analyze-string>
      </xsl:template>
      

      【讨论】:

      • 当我使用 Saxon 处理转换时,替换功能非常有用。 Internet Explorer 不支持替换功能吗?
      • replacexs:analyze-string 是 XSLT 2.0 的特性。我不知道任何 XSLT 2.0 浏览器支持,但我可能错了。检查此问题中提到的链接。他们应该有最新的信息:stackoverflow.com/questions/6282340/…
      猜你喜欢
      • 1970-01-01
      • 1970-01-01
      • 1970-01-01
      • 2011-11-25
      • 2013-09-05
      • 1970-01-01
      • 2013-02-08
      • 2019-05-07
      • 1970-01-01
      相关资源
      最近更新 更多