我有一个看起来像这样的XML文件,我试图用div包装彼此相邻的“Para_bb”节点。
<Para_a></Para_a>
<Para_a></Para_a>
<Para_bb></Para_bb>
<Para_bb></Para_bb>
<Para_bb></Para_bb>
<Para_bb></Para_bb>
<Para_a></Para_a>
<Para_bb></Para_bb>
<Para_bb></Para_bb>
<Para_a></Para_a>
<Para_a></Para_a>
<Para_bb></Para_bb>
我怎样才能让它看起来像这样?
<p></p>
<p></p>
<div class="blackBox">
<Para_bb></Para_bb>
<Para_bb></Para_bb>
<Para_bb></Para_bb>
<Para_bb></Para_bb>
</div>
<p></p>
<div class="blackBox">
<Para_bb></Para_bb>
<Para_bb></Para_bb>
</div>
<p></p>
<p></p>
<div class="blackBox">
<Para_bb></Para_bb>
</div>
答案 0 :(得分:4)
您可以按如下方式定义密钥:
<?xml version="1.0" encoding="UTF-8"?>
<xsl:stylesheet version="1.0" xmlns:xsl="http://www.w3.org/1999/XSL/Transform">
<xsl:output indent="yes"/>
<xsl:key name="group" match="Para_bb[preceding-sibling::*[1][self::Para_bb]]" use="generate-id(preceding-sibling::Para_bb[not(preceding-sibling::*[1][self::Para_bb])][1])"/>
<xsl:template match="Root">
<body>
<xsl:apply-templates/>
</body>
</xsl:template>
<xsl:template match="Para_a">
<p>
<xsl:apply-templates/>
</p>
</xsl:template>
<xsl:template match="Para_bb[preceding-sibling::*[1][self::Para_bb]]"/>
<xsl:template match="Para_bb[not(preceding-sibling::*[1][self::Para_bb])]">
<div class="blackBox">
<xsl:copy-of select=". | key('group', generate-id())"/>
</div>
</xsl:template>
</xsl:stylesheet>
改变
<Root>
<Para_a></Para_a>
<Para_a></Para_a>
<Para_bb>1</Para_bb>
<Para_bb>2</Para_bb>
<Para_bb>3</Para_bb>
<Para_bb>4</Para_bb>
<Para_a></Para_a>
<Para_bb>5</Para_bb>
<Para_bb>6</Para_bb>
<Para_a></Para_a>
<Para_a></Para_a>
<Para_bb>7</Para_bb>
</Root>
到
<body>
<p/>
<p/>
<div class="blackBox">
<Para_bb>1</Para_bb>
<Para_bb>2</Para_bb>
<Para_bb>3</Para_bb>
<Para_bb>4</Para_bb>
</div>
<p/>
<div class="blackBox">
<Para_bb>5</Para_bb>
<Para_bb>6</Para_bb>
</div>
<p/>
<p/>
<div class="blackBox">
<Para_bb>7</Para_bb>
</div>
</body>
答案 1 :(得分:3)
在XSLT 1.0中执行此操作的一种方法是使模板与组中每个 Para_bb 元素的第一个匹配项匹配
<xsl:template match="Para_bb[not(preceding-sibling::*[1][self::Para_bb])]">
然后,您将在第一个元素
上调用指定模式的新模板 <p>
<xsl:apply-templates select="." mode="div" />
</p>
然后,在匹配指定模式的 Para_bb 模板中,您将复制该元素,并选择下一个兄弟,但前提是它是另一个 Para_bb
<xsl:template match="Para_bb" mode="div">
<xsl:call-template name="identity" />
<xsl:apply-templates select="following-sibling::*[1][self::Para_bb]" mode="div"/>
</xsl:template>
(被调用的命名模板是标准身份模板)
试试这个XSLT
<xsl:stylesheet xmlns:xsl="http://www.w3.org/1999/XSL/Transform" version="1.0">
<xsl:output method="xml" indent="yes"/>
<xsl:template match="Para_bb[not(preceding-sibling::*[1][self::Para_bb])]">
<div class="blackBox">
<xsl:apply-templates select="." mode="div" />
</div>
</xsl:template>
<xsl:template match="Para_bb" />
<xsl:template match="Para_a">
<p>
<xsl:apply-templates select="@*|node()"/>
</p>
</xsl:template>
<xsl:template match="Para_bb" mode="div">
<xsl:call-template name="identity" />
<xsl:apply-templates select="following-sibling::*[1][self::Para_bb]" mode="div"/>
</xsl:template>
<xsl:template match="@*|node()" name="identity">
<xsl:copy>
<xsl:apply-templates select="@*|node()"/>
</xsl:copy>
</xsl:template>
</xsl:stylesheet>