使用XSLT获取位置(查找特定项目后的所有节点)

时间:2011-11-22 16:04:50

标签: xml xslt xpath

我正在尝试进行这样的转换。 考虑我有一个XML文件:

 <name>
   <a>Andy</a>
   <b>Emma</b>
   <c>John</c>
   <d>Cindy</d>
   <e>May</e>
 </name>

现在我希望在<b>Emma</b>元素之后选择所有元素,因此输出将如下所示:

<new>
  <one>John</one>
  <one>Cindy</one>
  <one>May</one>
<new>

我只能通过手动将条件声明为

来完成条件

[position()>2]

但是有没有办法自动获得这个位置?像这样的粗略想法:

[position()>Emma][position()>b]

3 个答案:

答案 0 :(得分:12)

您可以做的是/name/*[. = 'Emma']/following-sibling::*/name/b/following-sibling::*

答案 1 :(得分:3)

您无需获得该职位,您可以改为使用[preceding-sibling::*[text() = 'Emma']][preceding-sibling::b]

答案 2 :(得分:2)

这是一个完整的转型:

<xsl:stylesheet version="1.0"
 xmlns:xsl="http://www.w3.org/1999/XSL/Transform">
 <xsl:output omit-xml-declaration="yes" indent="yes"/>
 <xsl:strip-space elements="*"/>

 <xsl:template match="/*">
     <new>
      <xsl:apply-templates select=
       "*[. = 'Emma']/following-sibling::*"/>
     </new>
 </xsl:template>

 <xsl:template match="*/*">
  <one><xsl:value-of select="."/></one>
 </xsl:template>
</xsl:stylesheet>

将此转换应用于提供的XML文档

<name>
    <a>Andy</a>
    <b>Emma</b>
    <c>John</c>
    <d>Cindy</d>
    <e>May</e>
</name>

产生了想要的正确结果

<new>
   <one>John</one>
   <one>Cindy</one>
   <one>May</one>
</new>

另一种变体是使用以下匹配模式

*/*[not('Emma' = .|following-sibling::*)]

现在完全转型

<xsl:stylesheet version="1.0"
 xmlns:xsl="http://www.w3.org/1999/XSL/Transform">
 <xsl:output omit-xml-declaration="yes" indent="yes"/>
 <xsl:strip-space elements="*"/>

 <xsl:template match="/*">
     <new>
      <xsl:apply-templates/>
     </new>
 </xsl:template>

 <xsl:template match="*/*[not('Emma' = .|following-sibling::*)]">
  <one><xsl:value-of select="."/></one>
 </xsl:template>
 <xsl:template match="*/*" priority="0"/>
</xsl:stylesheet>
相关问题