XSL:如何替换字符串AND更改属性值

时间:2016-09-02 08:37:23

标签: xml xslt

我想实现更改atrribute值并用XSL替换元素的子字符串。

XML

<...>
   <communication type="telephone">123 456 789 </communication>
   <communication type="telephone">789 (EXT)</communication>
   <communication type="telephone">123 456 789 </communication>
</...>

应该是

<...>
   <communication type="telephone">123 456 789 </communication>
   <communication type="ext">789</communication>
   <communication type="telephone">123 456 789 </communication>
</...>

XSL(2.0)

<xsl:template match="communication[@type='telephone'][contains(text(),'(EXT)')]">
<xsl:copy>
    <xsl:value-of select="replace(., '(EXT)', '')"/>
    <xsl:attribute name="extension">true</xsl:attribute>
    <xsl:apply-templates select="@*|node()"/>
</xsl:copy>

Saxxon说 “在包含元素的子元素”

之后,无法创建属性节点

我没有实现更改属性类型的值,所以我创建了一个新属性。但即使使用这种解决方法,我也不知道如何使这两个要求(添加属性和删除子字符串)起作用。

任何解决这个问题的想法都非常感谢!

2 个答案:

答案 0 :(得分:1)

这部分:

<xsl:value-of select="replace(., '(EXT)', '')"/>

创建一个communication子项的文本节点。完成后,您将无法再创建communication的属性。您有两条尝试执行此操作的说明:

<xsl:attribute name="extension">true</xsl:attribute>

<xsl:apply-templates select="@*|node()"/>

@*)部分。

xsl:attribute指令必须先出现 - 您真的不想在这里使用xsl:apply-templates指令,因为您已经自己创建了所有内容。

另请注意,replace()不会替换括号。

当然,你可以通过以下方式简化:

<xsl:template match="communication[@type='telephone'][contains(text(),'(EXT)')]">
    <communication extension="true">
        <xsl:value-of select="replace(., '\(EXT\)', '')"/>
    </communication>
</xsl:template>

答案 1 :(得分:0)

我想你想要

<xsl:template match="communication[@type = 'telephone' and contains(., '(EXT)')]">
  <xsl:copy>
    <xsl:apply-templates select="@*"/>
    <xsl:attribute name="extension">true</xsl:attribute>
    <xsl:value-of select="replace(., '(EXT)', '')"/>
  </xsl:copy>
</xsl:template>