Xml XSLT 3.0-用数字字符串表示替换数字字符

Xml XSLT 3.0-用数字字符串表示替换数字字符,xml,xslt,Xml,Xslt,我正在尝试使用xslt创建xml数据集,目前面临的问题是,我正在尝试设置一些无效的元素名称、3RD_RACK、3DATA_VIEW,我尝试使用的是: <xsl:value-of select="translate(current()/@name), translate(current()/@name), 'abcdefghijklmnopqrstuvwxyzABCDEFGHIJKLMNOPQRSTUVWXYZ_', ''), '_')"/> 我想到的是用字符串表示替换所有数字,以便

我正在尝试使用xslt创建xml数据集,目前面临的问题是,我正在尝试设置一些无效的元素名称、3RD_RACK、3DATA_VIEW,我尝试使用的是:

<xsl:value-of select="translate(current()/@name), translate(current()/@name), 'abcdefghijklmnopqrstuvwxyzABCDEFGHIJKLMNOPQRSTUVWXYZ_', ''), '_')"/>
我想到的是用字符串表示替换所有数字,以便于进行xml验证,例如:

1->1 2->2

因此,最终我的输入变成:

3RD_RACK -> threeRD_RACK, ENERGY_CLASS_twozeroonezero, PROGRAMMDAUERPROGRAMone
但是,我无法通过尝试实现我的目标:

    <xsl:variable name="MyMap" select="
            map { 
            '1' : 'one', 
            '2' : 'two',
            '3' : 'three',
            '4' : 'four',
            '5' : 'five',
            '6' : 'six', 
            '7' : 'seven',
            '8' : 'eight',
            '9' : 'nine'}">
        </xsl:variable>

<xsl:value-of select="$MyMap(current()/@name)"/>

只返回数字,有人能帮我翻译字符串中出现的数字吗


提前感谢您的回答。

下面是一个示例,它使用XPath 3中的
分析字符串
函数将任何ASCII数字替换为映射中的名称:

<?xml version="1.0" encoding="UTF-8"?>
<xsl:stylesheet xmlns:xsl="http://www.w3.org/1999/XSL/Transform"
    xmlns:xs="http://www.w3.org/2001/XMLSchema"
    exclude-result-prefixes="#all"
    version="3.0">

  <xsl:output method="text"/>

  <xsl:variable name="MyMap" select="
            map { 
            '0' : 'zero',
            '1' : 'one', 
            '2' : 'two',
            '3' : 'three',
            '4' : 'four',
            '5' : 'five',
            '6' : 'six', 
            '7' : 'seven',
            '8' : 'eight',
            '9' : 'nine'}">
        </xsl:variable>

  <xsl:param name="names"
    as="xs:string*"
    select="'3RD_RACK', 'ENERGY_CLASS_2010', 'PROGRAMMDAUERPROGRAM1'"/>

  <xsl:variable name="converted-names"
    as="xs:string*"
    select="$names ! string-join(analyze-string(., '[0-9]')/*/(if (self::*:match) then $MyMap(.) else string()))"/>

  <xsl:template match="/">
      <xsl:value-of 
        select="$converted-names" separator="&#10;"/>
  </xsl:template>

</xsl:stylesheet>

下面是一个示例,它使用XPath 3中的
分析字符串
函数将任何ASCII数字替换为映射中的名称:

<?xml version="1.0" encoding="UTF-8"?>
<xsl:stylesheet xmlns:xsl="http://www.w3.org/1999/XSL/Transform"
    xmlns:xs="http://www.w3.org/2001/XMLSchema"
    exclude-result-prefixes="#all"
    version="3.0">

  <xsl:output method="text"/>

  <xsl:variable name="MyMap" select="
            map { 
            '0' : 'zero',
            '1' : 'one', 
            '2' : 'two',
            '3' : 'three',
            '4' : 'four',
            '5' : 'five',
            '6' : 'six', 
            '7' : 'seven',
            '8' : 'eight',
            '9' : 'nine'}">
        </xsl:variable>

  <xsl:param name="names"
    as="xs:string*"
    select="'3RD_RACK', 'ENERGY_CLASS_2010', 'PROGRAMMDAUERPROGRAM1'"/>

  <xsl:variable name="converted-names"
    as="xs:string*"
    select="$names ! string-join(analyze-string(., '[0-9]')/*/(if (self::*:match) then $MyMap(.) else string()))"/>

  <xsl:template match="/">
      <xsl:value-of 
        select="$converted-names" separator="&#10;"/>
  </xsl:template>

</xsl:stylesheet>

简单的解决方案是使用其他字符对数字进行编码。然后你可以做一些简单的事情,比如:

<xsl:element name="{translate(@name, '1234567890', 'αβγδεζηθικλμνξο')}">
    <xsl:apply-templates/>
</xsl:element>
它似乎并不比XSLT3.0更详细


添加:

我忘了提到最重要的一点:还有其他一些方法可以使字符串不符合规则。如果不能确定提供的名称是否为有效的XML元素名称,那么最合适的做法是:

<elem name="{@name}">
   <xsl:apply-templates/>
</elem>


这是最简单同时也是最安全的解决方案。

简单的解决方案是使用其他字符对数字进行编码。然后你可以做一些简单的事情,比如:

<xsl:element name="{translate(@name, '1234567890', 'αβγδεζηθικλμνξο')}">
    <xsl:apply-templates/>
</xsl:element>
它似乎并不比XSLT3.0更详细


添加:

我忘了提到最重要的一点:还有其他一些方法可以使字符串不符合规则。如果不能确定提供的名称是否为有效的XML元素名称,那么最合适的做法是:

<elem name="{@name}">
   <xsl:apply-templates/>
</elem>


这是最简单、同时也是最安全的解决方案。

如果字符串是数字,那么只替换字符串的第一个字符就足够了吗?我会首先选中
not(current()/@name castable as xs:NCName)
,否则您不必替换任何内容,只需使用该值即可。至于替换数字的策略,我同意Michael的观点,即如果第一个字符是数字,则只需替换第一个字符。分解该字符串可以通过各种方式完成,使用子字符串、使用分析字符串、使用字符串到代码点。感谢您的建议,通常我已经实现了与Michael建议的相同的技术,目前这涵盖了我,我可以创建我的数据集。但是我只是想知道如何做到这一点,然后在这里问,如何实现这一目标容易。对于其他类型的需求也会有帮助。不需要更改(替换)任何数字。如果我有你的问题,我会简单地在任何以数字开头的字符串前面加上'N',这要容易得多。如果您想让我用此解决方案发布答案,请务必告诉我。如果字符串是数字,仅替换字符串的第一个字符是否足够?我将首先选中
not(current()/@name castable as xs:NCName)
,否则您不必替换任何内容,只需使用该值即可。至于替换数字的策略,我同意Michael的观点,即如果第一个字符是数字,则只需替换第一个字符。分解该字符串可以通过各种方式完成,使用子字符串、使用分析字符串、使用字符串到代码点。感谢您的建议,通常我已经实现了与Michael建议的相同的技术,目前这涵盖了我,我可以创建我的数据集。但是我只是想知道如何做到这一点,然后在这里问,如何实现这一目标容易。对于其他类型的需求也会有帮助。不需要更改(替换)任何数字。如果我有你的问题,我会简单地在任何以数字开头的字符串前面加上'N',这要容易得多。如果您想让我发布此解决方案的答案,请务必告诉我。特别是,当将其与“not(current()/@name castable as xs:NCName)”结合使用时,只需再次检查“谢谢”!特别是,当将其与“not(current()/@name castable as xs:NCName)”结合使用时,只需再次检查“谢谢”,这是一件好事!