2016-05-05 2 views
2

テキストノードと、 'i'または ''または 'list'のようないくつかの要素を 'p'要素内にグループ化する方法をお勧めします。 divは子供がpにならないようにしてください。特定のタイプのテキストノードと隣接要素をグループ化する

XML:

<article> 
<body> 
    <para> 
     <display><fig>Fig1</fig></display> 
     the text node1 
    </para> 
    <para> 
     <display><fig>Fig1</fig></display> 
    </para> 
    <para> 
     <display><fig>Fig1</fig></display> 
     the text node1 <i>h</i> ther <b>b</b> the text4 
     <display><tab>Table1</tab></display> 
     the text node2 
     <list><li>list1</li></list> 
    </para> 
    <para>The text node3</para> 

</body> 
</article> 

XML(改行や空白表示目的のために、第2回XML下記の使用を実行すると):(改行なし)

<article><body><para><display><fig>Fig1</fig></display>the text node1</para><para><display><fig>Fig1</fig></display></para><para><display><fig>Fig1</fig></display>the text node1 <i>h</i> ther <b>b</b> the text4<display><tab>Table1</tab></display>the text node2<list><li>list1</li></list></para><para>The text node3</para></body></article> 

XSLT :

<xsl:stylesheet xmlns:xsl="http://www.w3.org/1999/XSL/Transform" version="2.0"> 

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

<xsl:template match="para"> 
    <xsl:choose> 
     <xsl:when test="not(text())"><xsl:apply-templates/></xsl:when> 
     <xsl:when test="display and text() or *"> 
      <xsl:for-each select="node()"> 
       <xsl:choose> 
        <xsl:when test="name()='display'"><div><xsl:apply-templates/></div></xsl:when> 
        <xsl:when test="name()='i' or name()='b'"> 
         <xsl:copy><xsl:apply-templates select="@*|node()"/></xsl:copy> 
        </xsl:when> 
        <xsl:when test="not(*)"><p><xsl:value-of select="."/></p></xsl:when><!--Here grouping required with adjacent elements 'i' or 'b' etc --> 
        <xsl:otherwise><p><xsl:apply-templates/></p></xsl:otherwise> 
       </xsl:choose> 
      </xsl:for-each> 
     </xsl:when> 
     <xsl:otherwise> 
      <p><xsl:apply-templates/></p> 
     </xsl:otherwise> 
    </xsl:choose> 
</xsl:template> 
</xsl:stylesheet> 

必要な結果は:

<article> 
<body> 
    <div><fig>Fig1</fig></div><!--ensure div should not child to 'p'--> 
    <p>the text node1</p>  <!--Text area including 'i' and 'b' to be within 'p' --> 
    <div><fig>Fig1</fig></div> 
    <div><fig>Fig1</fig></div> 
    <p>the text node1 <i>h</i> ther <b>b</b> the text4</p><!--Text area including 'i' and 'b' to be within 'p' --> 
    <div><tab>Table1</tab></div> 
    <p>the text node2<list><li>list1</li></list></p><!--text area includes 'list' element --> 
    <p>The text node3</p> 
</body> 
</article> 

答えて

3

あなたがXSLT 2.0を使用しているとして、あなたは彼らがdisplay要素であるかどうかに応じて、グループの隣接する子ノードに、ここxsl:for-each-groupを利用することができます。だから、

<xsl:for-each-group select="node()" group-adjacent="boolean(self::display)"> 

display以外のノードはfalseのグループ化キーを持っていますので、一緒にグループ化することが、あなたがそれらをラップすることができpタグで

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

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

<xsl:template match="para"> 
    <xsl:for-each-group select="node()" group-adjacent="boolean(self::display)"> 
    <xsl:choose> 
     <xsl:when test="current-grouping-key()"> 
      <xsl:apply-templates select="current-group()" /> 
     </xsl:when> 
     <xsl:otherwise> 
      <p> 
       <xsl:apply-templates select="current-group()" /> 
      </p> 
     </xsl:otherwise> 
     </xsl:choose> 
    </xsl:for-each-group> 
</xsl:template> 

<xsl:template match="display"> 
    <div> 
    <xsl:apply-templates /> 
    </div> 
</xsl:template> 
</xsl:stylesheet> 
+0

おかげさまで素晴らしい提案をいただき、ありがとうございました。 –

1

このXSLTをお試しください私はあなたが使用できると思いますfor-each-group group-adjacent="boolean(self::text() | self::i |.."

<xsl:stylesheet xmlns:xsl="http://www.w3.org/1999/XSL/Transform" 
    xmlns:xs="http://www.w3.org/2001/XMLSchema" 
    exclude-result-prefixes="xs" 
    version="2.0"> 

    <xsl:output indent="yes"/> 

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

    <xsl:template match="para"> 
     <xsl:for-each-group select="node()" group-adjacent="boolean(self::text() | self::i | self::b | self::list)"> 
      <xsl:choose> 
       <xsl:when test="current-grouping-key()"> 
        <p> 
         <xsl:apply-templates select="current-group()"/> 
        </p> 
       </xsl:when> 
       <xsl:otherwise> 
        <xsl:apply-templates select="current-group()"/> 
       </xsl:otherwise> 
      </xsl:choose> 
     </xsl:for-each-group> 
    </xsl:template> 

    <xsl:template match="display"> 
     <div> 
      <xsl:apply-templates/> 
     </div> 
    </xsl:template> 

</xsl:stylesheet> 
+0

提案ありがとう、ありがとう。 –

関連する問題