【问题标题】:Reaching the child node in different order from parent nodes in XSLT以与 XSLT 中的父节点不同的顺序到达子节点
【发布时间】:2018-07-18 23:29:35
【问题描述】:

我一直在尝试解决 XSLT 中的一个问题,即到达特定父节点的子节点,而不管该父节点中的顺序如何。

假设我们有一个 xml 文件:

<book>
   <id>
      <type>
           <name name="something">
              --SomeText
           </name>
      </type>
    <id>
</book>
<book>
   <name name="something">

   <name>
   <id>
      --SomeNodes--
   </id>
   <number>
   </number>
</book>

这里的想法是我有很多这样的节点集,每个节点都有不同的&lt;name&gt; 节点顺序。

我想要的是,不管这个顺序,每次和book节点匹配,我应该都能得到&lt;name&gt;节点的值。

XSLT:

<xsl:template match="book">

 <xsl:param name="rule" select="//name[1]>
    <xsl:copy>
        <xsl:apply-templates select="@* | node()"/>
    </xsl:copy>
   <xsl:if test=name/@name>
       <xsl:comment><xsl:value-of select="concat('some text', substring($rule,2,4))"/>
   </xsl:if>
</xsl:template>

所以,显然我用这种方法得到了节点的所有结果,因为“//”。

如果我将其更改为不带“//”的名称[1],那么它只会在书之后找到第一个名称元素,而不会找到其他元素。

每次当我匹配和完全相同的节点值时如何递归获取并将其值写为模板后的注释。

注意:我给你的例子是 XML,但我是从 XSLT-XSLT 转换的。

【问题讨论】:

  • 如果您输入的 XML 格式正确,我们的生活会更轻松。这不是一个轻率的评论:我实际上不知道您输入中的结束标签应该在哪里。
  • 我在匹配 节点时成功了,但我想通过 节点来完成。所以我认为 也可以有所帮助,我尝试了一点但没有成功。

标签: xml xslt


【解决方案1】:

我认为,当您对此类杂乱的数据进行任何类型的转换时,最好将其作为 2-pass 过程进行:首先整理数据,然后将其转换为您想要的形式。这样,整理数据的过程是可重复使用和独立的。

您只给出了输入格式的草图,但我将从转换书籍元素开始,以便名称始终是顶级子元素:

<xsl:template match="book">
  <xsl:copy>
    <name><xsl:value-of select=".//name"/></name>
    etc.
  </xsl:copy>
</xsl:template>

整理完数据后,下一步就相当简单了。

【讨论】:

    【解决方案2】:

    您可以尝试将其与&lt;name&gt; 匹配,而不是将模板与&lt;book&gt; 匹配。

    <xsl:template match="name">
        <book>
            <xsl:copy>
                <xsl:apply-templates select="@name" />
            </xsl:copy>
        </book>
    </xsl:template>
    

    输出

    <book>
        <name>something</name>
    </book>
    <book>
        <name>something</name>
    </book>
    

    【讨论】:

    • 是的,我想过,但是评论将在“名称”节点之后,我希望它在 节点之后,因为顺序不同,并且之前有很多元素后。可能很难选择那个父节点?
    • 你能分享一下预期的输出吗?我认为您仍然可以在通过name 节点访问时使用ancestor 轴在book 之后添加评论,类似于ancestor::book。由于缺少很多结束标记,因此很难从共享的 XML 和 XSLT 中分辨出来。
    • 我通过匹配 节点找到了解决方案。但是就像我说的那样,然后 cmets 在 节点下而不是在 下,我尝试了 但无法使其正常工作。
    猜你喜欢
    • 1970-01-01
    • 1970-01-01
    • 2017-05-04
    • 1970-01-01
    • 2017-12-06
    • 2015-05-15
    • 1970-01-01
    • 1970-01-01
    • 2016-07-16
    相关资源
    最近更新 更多