【问题标题】:Trying to read xml element value in xsl试图在 xsl 中读取 xml 元素值
【发布时间】:2013-04-15 15:59:59
【问题描述】:

我是XSL 的新手。我正在尝试使用 XSL 文件读取 XML 元素的值。我的 XML 文件是这样的:

<PersonList>
  <Person>
    <Name>person1</Name>
    <Age>21</Age>
  </Person>
  <Person>
    <Name>person2</Name>
    <Age>21</Age>
  </Person>
</PersonList>

我的 XSL 文件是这样的:

<xsl:stylesheet version="1.0" xmlns=...>
  <xsl:output method="xml" indent="yes" encoding="utf-8" omit-xml declaration="no" />
  <xsl template match="/">
    <PersonList>
      <xsl:for-each select="PersonList/Person">
        <Person>
          <xsl:for-each select="*">
            <xsl:variable name="elementName">
              <xsl:value-of select="name(.)" />
            </xsl:variable>
            <xsl:variable name="elementValue">
              ???
            </xsl:variable>
          </xsl:for-each>
        </Person>
      </xsl:for-each>
    </PersonList> 
  </xsl:template>
</xsl:stylesheet>

我应该如何替换??? 以获取存储在elementName 变量中的元素的值。我分别尝试了以下三行:

<xsl:value-of select="value(.)" /> 
<xsl:value-of select="value($elementName)" />
<xsl:value-of select="$elementName" />

但没有运气。请帮忙!

【问题讨论】:

  • 考虑发布您希望使用 XSLT 为您发布的 XML 输入示例创建的 XML 结果。很难从您的 XSLT 示例中看出您想要实现什么,因为它存在 xsl template 之类的语法错误和空 for-each 主体之类的逻辑缺陷,或者使用上下文节点是根节点的 name(.)
  • 我已经更正了 xsl。请现在考虑。我想在循环中获取 elementValue 变量中的值 Person1、21、Person2、21。
  • 您应该真正了解 pull 处理(您正在执行的操作)和 push 样式之间的区别。对于这样的任务,使用模板和应用模板的推送样式更加自然,并且与 XSL 处理器的工作方式相匹配。看起来您只是想将输入复制到输出...在 Google 上搜索“XSL 身份模板”。

标签: xml xslt xslt-1.0


【解决方案1】:

您的?????????????????? 可以是&lt;xsl:value-of select="."/&gt;(即上下文元素的字符串值。)它与$elementName 没有任何联系。

您可以像这样更简洁地做到这一点:

<xsl:for-each select="*">
  <xsl:variable name="elementName" select="name()"/>
  <xsl:variable name="elementValue" select="string(.)"/>
</xsl:for-each>

但是你的模板真的很奇怪。您正在收集这些变量,但您没有对它们做任何事情——它们不会出现在输出中。你想得到什么输出?

使用for-each 通常是一种代码味道。在几乎所有情况下,您最好使用多个模板:

<xsl:stylesheet version="1.0" xmlns:xsl="http://www.w3.org/1999/XSL/Transform">
<xsl:output method="xml" indent="yes" encoding="utf-8" omit-xml-declaration="no" />

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

<xsl:template match="Person/*">
    <xsl:variable name="elementName" select="name()"/>
    <xsl:variable name="elementValue" select="string(.)"/>
</xsl:template>

</xsl:stylesheet>

这种复制几乎所有内容并仅更改一点 xml 的模式非常常见且非常强大,您应该 learn how to use it

【讨论】:

  • 感谢您的回答。这不是完整的 xsl。其实我需要根据元素中的值来修改xml。
  • 您是否考虑过使用模板而不是嵌套的for-each 循环?
  • 我是 xsl 的新手。不太了解使用模板。
【解决方案2】:

好吧,如果您真的想获取名称保存在变量中的元素的值,在您的情况下,您可以这样做

<xsl:variable name="elementValue">
    <xsl:value-of select="../*[name()=$elementName]" />
</xsl:variable>

但是,这是非常复杂的事情。您处于 xsl:for-each 循环中,迭代 Person 的子元素。因此,由于您已经定位到需要其值的元素,因此您可以这样做而忘记 elementName 变量。

<xsl:variable name="elementValue">
    <xsl:value-of select="."/>
</xsl:variable>

事实上,你可以将你的循环简化成这样

<xsl:for-each select="PersonList/Person">
   <Person>
      <xsl:for-each select="*">
         <xsl:value-of select="." />
      </xsl:for-each>
   </Person>
</xsl:for-each>

【讨论】:

    猜你喜欢
    • 1970-01-01
    • 1970-01-01
    • 1970-01-01
    • 1970-01-01
    • 1970-01-01
    • 1970-01-01
    • 1970-01-01
    • 1970-01-01
    • 1970-01-01
    相关资源
    最近更新 更多