0

我想修改名为“FOO”的元素的属性值,所以我写道:

<xsl:stylesheet version="1.0" xmlns:xsl="http://www.w3.org/1999/XSL/Transform">
   <xsl:output method="xml" indent="yes"/>

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

  <xsl:template match="FOO/@extent">
      <xsl:attribute name="extent">
      <xsl:text>1.5cm</xsl:text>
      </xsl:attribute>
  </xsl:template>

</xsl:stylesheet>

这东西有效。现在我需要同样的东西,但使用元素“fs:BOO”。我尝试用“fs:BOO”替换 FOO,但 xsltproc 说它不能编译这样的代码。我以这种方式临时解决了这个问题:

sed 's|fs:BOO|fs_BOO|g' | xsltproc stylesheet.xsl - | sed 's|fs_BOO|fs:BOO|g'

但可能有更简单的解决方案,而不使用“sed”?

输入数据示例:

<root>
    <fs:BOO extent="0mm" />
</root>

如果写:

<xsl:template match="fs:BOO/@extent">

我有:

xsltCompileStepPattern : no namespace bound to prefix fs
compilation error: file test.xsl line 10 element template
xsltCompilePattern : failed to compile 'fs:BOO/@extent'
4

1 回答 1

1

首先,我希望您的 XML 具有命名空间的声明,否则它将无效

<root xmlns:fs="www.foo.com">
    <fs:BOO extent="0mm" />
</root>

这也适用于您的 XSLT。如果您尝试这样做,<xsl:template match="fs:BOO/@extent">那么您也需要在 XSLT 中声明命名空间。

<xsl:stylesheet version="1.0" 
   xmlns:xsl="http://www.w3.org/1999/XSL/Transform" 
   xmlns:fs="www.foo.com">

重要的是命名空间 URI 与 XML 中的匹配。

但是,如果您想处理不同的命名空间,您可以采用不同的方法。您可以使用local-name()函数来检查没有命名空间前缀的元素名称。

试试这个 XSLT

<xsl:stylesheet version="1.0" xmlns:xsl="http://www.w3.org/1999/XSL/Transform">
   <xsl:output method="xml" indent="yes"/>

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

  <xsl:template match="*[local-name()='BOO']/@extent">
      <xsl:attribute name="extent">
         <xsl:text>1.5cm</xsl:text>
      </xsl:attribute>
  </xsl:template>
</xsl:stylesheet>

这应该输出以下内容

<root xmlns:fs="fs">
   <fs:BOO extent="1.5cm"></fs:BOO>
</root>
于 2012-11-01T08:09:15.333 回答