如何用XSLT仅选取嵌套树中每个dependency-rules的首个name节点
解决方案(XSLT 1.0)
直接通过递归模板匹配每个dependency-rules节点,只处理其第一个子name节点,同时用缩进体现层级关系:
<xsl:stylesheet version="1.0" xmlns:xsl="http://www.w3.org/1999/XSL/Transform"> <xsl:output method="text" encoding="UTF-8"/> <!-- 从根节点启动递归处理 --> <xsl:template match="/"> <xsl:apply-templates select="someXML/dependency-rules"/> </xsl:template> <!-- 匹配dependency-rules,仅处理第一个子name节点 --> <xsl:template match="dependency-rules"> <xsl:if test="name[1]"> <!-- 根据层级深度生成缩进 --> <xsl:call-template name="indent"> <xsl:with-param name="depth" select="count(ancestor::dependency-rules)"/> </xsl:call-template> <!-- 输出name的纯文本,清理多余空格 --> <xsl:value-of select="normalize-space(name[1]/text())"/> <xsl:text> </xsl:text> <!-- 换行 --> <!-- 递归处理当前name下的嵌套dependency-rules --> <xsl:apply-templates select="name[1]/dependency-rules"/> </xsl:if> </xsl:template> <!-- 生成缩进的辅助模板 --> <xsl:template name="indent"> <xsl:param name="depth" select="0"/> <xsl:if test="$depth > 0"> <xsl:text> </xsl:text> <!-- 用两个空格表示一级缩进 --> <xsl:call-template name="indent"> <xsl:with-param name="depth" select="$depth - 1"/> </xsl:call-template> </xsl:if> </xsl:template> <!-- 忽略无关文本节点,避免多余输出 --> <xsl:template match="text()"/> </xsl:stylesheet>
代码说明
- 精准节点选择:每次只处理
dependency-rules下的第一个name子节点,彻底避免匹配所有name导致的重复输出问题。 - 层级缩进控制:通过
indent模板根据节点的祖先层级数生成对应空格,直观体现嵌套关系。 - 递归嵌套处理:处理完当前
name后,自动递归处理其内部的dependency-rules,实现完整的层级遍历。 - 文本清理:用
normalize-space去除name文本中的冗余换行和空格,保证输出格式整洁。
最终输出
将你的XML输入上述XSLT后,会得到符合预期的结果:
FONDS CATEGORY
内容的提问来源于stack exchange,提问作者RolfBly
相关产品推荐
相关产品推荐

